Mercurial > hg > rc1
changeset 50:e09cef17c56c
stale confused Ssabre stuff
| author | Charlie Root |
|---|---|
| date | Mon, 06 Oct 2025 12:32:10 -0400 |
| parents | 91f005a4f7e9 |
| children | b80b258cc02c |
| files | plugins/libcalendaring/composer.json plugins/libcalendaring/lib/Sabre/VObject/Component.php plugins/libcalendaring/lib/Sabre/VObject/Component/VAlarm.php plugins/libcalendaring/lib/Sabre/VObject/Component/VCalendar.php plugins/libcalendaring/lib/Sabre/VObject/Component/VCard.php plugins/libcalendaring/lib/Sabre/VObject/Component/VEvent.php plugins/libcalendaring/lib/Sabre/VObject/Component/VFreeBusy.php plugins/libcalendaring/lib/Sabre/VObject/Component/VJournal.php plugins/libcalendaring/lib/Sabre/VObject/Component/VTodo.php plugins/libcalendaring/lib/Sabre/VObject/DateTimeParser.php plugins/libcalendaring/lib/Sabre/VObject/Document.php plugins/libcalendaring/lib/Sabre/VObject/ElementList.php plugins/libcalendaring/lib/Sabre/VObject/FreeBusyGenerator.php plugins/libcalendaring/lib/Sabre/VObject/Node.php plugins/libcalendaring/lib/Sabre/VObject/Parameter.php plugins/libcalendaring/lib/Sabre/VObject/ParseException.php plugins/libcalendaring/lib/Sabre/VObject/Property.php plugins/libcalendaring/lib/Sabre/VObject/Property/Compound.php plugins/libcalendaring/lib/Sabre/VObject/Property/DateTime.php plugins/libcalendaring/lib/Sabre/VObject/Property/MultiDateTime.php plugins/libcalendaring/lib/Sabre/VObject/Reader.php plugins/libcalendaring/lib/Sabre/VObject/RecurrenceIterator.php plugins/libcalendaring/lib/Sabre/VObject/Splitter/ICalendar.php plugins/libcalendaring/lib/Sabre/VObject/Splitter/SplitterInterface.php plugins/libcalendaring/lib/Sabre/VObject/Splitter/VCard.php plugins/libcalendaring/lib/Sabre/VObject/StringUtil.php plugins/libcalendaring/lib/Sabre/VObject/TimeZoneUtil.php plugins/libcalendaring/lib/Sabre/VObject/Version.php plugins/libcalendaring/lib/Sabre/VObject/includes.php vendor/autoload.php vendor/sabre/vobject/.gitignore vendor/sabre/vobject/.travis.yml vendor/sabre/vobject/ChangeLog.md vendor/sabre/vobject/LICENSE vendor/sabre/vobject/README.md vendor/sabre/vobject/bin/bench.php vendor/sabre/vobject/bin/fetch_windows_zones.php vendor/sabre/vobject/bin/generate_vcards vendor/sabre/vobject/bin/generateicalendardata.php vendor/sabre/vobject/bin/vobject vendor/sabre/vobject/composer.json vendor/sabre/vobject/lib/Cli.php vendor/sabre/vobject/lib/Component.php vendor/sabre/vobject/lib/Component/VAlarm.php vendor/sabre/vobject/lib/Component/VCalendar.php vendor/sabre/vobject/lib/Component/VCard.php vendor/sabre/vobject/lib/Component/VEvent.php vendor/sabre/vobject/lib/Component/VFreeBusy.php vendor/sabre/vobject/lib/Component/VJournal.php vendor/sabre/vobject/lib/Component/VTimeZone.php vendor/sabre/vobject/lib/Component/VTodo.php vendor/sabre/vobject/lib/DateTimeParser.php vendor/sabre/vobject/lib/Document.php vendor/sabre/vobject/lib/ElementList.php vendor/sabre/vobject/lib/EofException.php vendor/sabre/vobject/lib/FreeBusyGenerator.php vendor/sabre/vobject/lib/ITip/Broker.php vendor/sabre/vobject/lib/ITip/ITipException.php vendor/sabre/vobject/lib/ITip/Message.php vendor/sabre/vobject/lib/ITip/SameOrganizerForAllComponentsException.php vendor/sabre/vobject/lib/Node.php vendor/sabre/vobject/lib/Parameter.php vendor/sabre/vobject/lib/ParseException.php vendor/sabre/vobject/lib/Parser/Json.php vendor/sabre/vobject/lib/Parser/MimeDir.php vendor/sabre/vobject/lib/Parser/Parser.php vendor/sabre/vobject/lib/Property.php vendor/sabre/vobject/lib/Property/Binary.php vendor/sabre/vobject/lib/Property/Boolean.php vendor/sabre/vobject/lib/Property/FlatText.php vendor/sabre/vobject/lib/Property/Float.php vendor/sabre/vobject/lib/Property/ICalendar/CalAddress.php vendor/sabre/vobject/lib/Property/ICalendar/Date.php vendor/sabre/vobject/lib/Property/ICalendar/DateTime.php vendor/sabre/vobject/lib/Property/ICalendar/Duration.php vendor/sabre/vobject/lib/Property/ICalendar/Period.php vendor/sabre/vobject/lib/Property/ICalendar/Recur.php vendor/sabre/vobject/lib/Property/Integer.php vendor/sabre/vobject/lib/Property/Text.php vendor/sabre/vobject/lib/Property/Time.php vendor/sabre/vobject/lib/Property/Unknown.php vendor/sabre/vobject/lib/Property/Uri.php vendor/sabre/vobject/lib/Property/UtcOffset.php vendor/sabre/vobject/lib/Property/VCard/Date.php vendor/sabre/vobject/lib/Property/VCard/DateAndOrTime.php vendor/sabre/vobject/lib/Property/VCard/DateTime.php vendor/sabre/vobject/lib/Property/VCard/LanguageTag.php vendor/sabre/vobject/lib/Property/VCard/TimeStamp.php vendor/sabre/vobject/lib/Reader.php vendor/sabre/vobject/lib/Recur/EventIterator.php vendor/sabre/vobject/lib/Recur/NoInstancesException.php vendor/sabre/vobject/lib/Recur/RDateIterator.php vendor/sabre/vobject/lib/Recur/RRuleIterator.php vendor/sabre/vobject/lib/RecurrenceIterator.php vendor/sabre/vobject/lib/Splitter/ICalendar.php vendor/sabre/vobject/lib/Splitter/SplitterInterface.php vendor/sabre/vobject/lib/Splitter/VCard.php vendor/sabre/vobject/lib/StringUtil.php vendor/sabre/vobject/lib/TimeZoneUtil.php vendor/sabre/vobject/lib/UUIDUtil.php vendor/sabre/vobject/lib/VCardConverter.php vendor/sabre/vobject/lib/Version.php vendor/sabre/vobject/lib/timezonedata/exchangezones.php vendor/sabre/vobject/lib/timezonedata/lotuszones.php vendor/sabre/vobject/lib/timezonedata/php-bc.php vendor/sabre/vobject/lib/timezonedata/php-workaround.php vendor/sabre/vobject/lib/timezonedata/windowszones.php vendor/sabre/vobject/tests/VObject/AttachIssueTest.php vendor/sabre/vobject/tests/VObject/CliTest.php vendor/sabre/vobject/tests/VObject/Component/VAlarmTest.php vendor/sabre/vobject/tests/VObject/Component/VCalendarTest.php vendor/sabre/vobject/tests/VObject/Component/VCardTest.php vendor/sabre/vobject/tests/VObject/Component/VEventTest.php vendor/sabre/vobject/tests/VObject/Component/VFreeBusyTest.php vendor/sabre/vobject/tests/VObject/Component/VJournalTest.php vendor/sabre/vobject/tests/VObject/Component/VTimeZoneTest.php vendor/sabre/vobject/tests/VObject/Component/VTodoTest.php vendor/sabre/vobject/tests/VObject/ComponentTest.php vendor/sabre/vobject/tests/VObject/DateTimeParserTest.php vendor/sabre/vobject/tests/VObject/DocumentTest.php vendor/sabre/vobject/tests/VObject/ElementListTest.php vendor/sabre/vobject/tests/VObject/EmClientTest.php vendor/sabre/vobject/tests/VObject/EmptyParameterTest.php vendor/sabre/vobject/tests/VObject/EmptyValueIssueTest.php vendor/sabre/vobject/tests/VObject/FreeBusyGeneratorTest.php vendor/sabre/vobject/tests/VObject/GoogleColonEscapingTest.php vendor/sabre/vobject/tests/VObject/ICalendar/AttachParseTest.php vendor/sabre/vobject/tests/VObject/ITip/BrokerAttendeeReplyTest.php vendor/sabre/vobject/tests/VObject/ITip/BrokerDeleteEventTest.php vendor/sabre/vobject/tests/VObject/ITip/BrokerNewEventTest.php vendor/sabre/vobject/tests/VObject/ITip/BrokerProcessMessageTest.php vendor/sabre/vobject/tests/VObject/ITip/BrokerProcessReplyTest.php vendor/sabre/vobject/tests/VObject/ITip/BrokerTester.php vendor/sabre/vobject/tests/VObject/ITip/BrokerUpdateEventTest.php vendor/sabre/vobject/tests/VObject/ITip/EvolutionTest.php vendor/sabre/vobject/tests/VObject/ITip/MessageTest.php vendor/sabre/vobject/tests/VObject/Issue153Test.php vendor/sabre/vobject/tests/VObject/Issue26Test.php vendor/sabre/vobject/tests/VObject/Issue36WorkAroundTest.php vendor/sabre/vobject/tests/VObject/Issue40Test.php vendor/sabre/vobject/tests/VObject/Issue64Test.php vendor/sabre/vobject/tests/VObject/Issue96Test.php vendor/sabre/vobject/tests/VObject/JCalTest.php vendor/sabre/vobject/tests/VObject/JCardTest.php vendor/sabre/vobject/tests/VObject/LineFoldingIssueTest.php vendor/sabre/vobject/tests/VObject/ParameterTest.php vendor/sabre/vobject/tests/VObject/Parser/JsonTest.php vendor/sabre/vobject/tests/VObject/Parser/MimeDirTest.php vendor/sabre/vobject/tests/VObject/Parser/QuotedPrintableTest.php vendor/sabre/vobject/tests/VObject/Property/BinaryTest.php vendor/sabre/vobject/tests/VObject/Property/BooleanTest.php vendor/sabre/vobject/tests/VObject/Property/CompoundTest.php vendor/sabre/vobject/tests/VObject/Property/FloatTest.php vendor/sabre/vobject/tests/VObject/Property/ICalendar/CalAddressTest.php vendor/sabre/vobject/tests/VObject/Property/ICalendar/DateTimeTest.php vendor/sabre/vobject/tests/VObject/Property/ICalendar/DurationTest.php vendor/sabre/vobject/tests/VObject/Property/ICalendar/RecurTest.php vendor/sabre/vobject/tests/VObject/Property/TextTest.php vendor/sabre/vobject/tests/VObject/Property/VCard/DateAndOrTimeTest.php vendor/sabre/vobject/tests/VObject/Property/VCard/LanguageTagTest.php vendor/sabre/vobject/tests/VObject/PropertyTest.php vendor/sabre/vobject/tests/VObject/ReaderTest.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/ByMonthInDailyTest.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/FifthTuesdayProblemTest.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/IncorrectExpandTest.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/InfiniteLoopProblemTest.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/Issue48Test.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/Issue50Test.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/MainTest.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/MissingOverriddenTest.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/NoInstancesTest.php vendor/sabre/vobject/tests/VObject/Recur/EventIterator/OverrideFirstEventTest.php vendor/sabre/vobject/tests/VObject/Recur/RDateIteratorTest.php vendor/sabre/vobject/tests/VObject/Recur/RRuleIteratorTest.php vendor/sabre/vobject/tests/VObject/RecurrenceIterator/UntilRespectsTimezoneTest.ics vendor/sabre/vobject/tests/VObject/SlashRTest.php vendor/sabre/vobject/tests/VObject/Splitter/ICalendarTest.php vendor/sabre/vobject/tests/VObject/Splitter/VCardTest.php vendor/sabre/vobject/tests/VObject/StringUtilTest.php vendor/sabre/vobject/tests/VObject/TestCase.php vendor/sabre/vobject/tests/VObject/TimeZoneUtilTest.php vendor/sabre/vobject/tests/VObject/UUIDUtilTest.php vendor/sabre/vobject/tests/VObject/VCard21Test.php vendor/sabre/vobject/tests/VObject/VCardConverterTest.php vendor/sabre/vobject/tests/VObject/VersionTest.php vendor/sabre/vobject/tests/VObject/issue153.vcf vendor/sabre/vobject/tests/VObject/issue64.vcf vendor/sabre/vobject/tests/bootstrap.php vendor/sabre/vobject/tests/phpcs/ruleset.xml vendor/sabre/vobject/tests/phpunit.xml |
| diffstat | 190 files changed, 0 insertions(+), 37581 deletions(-) [+] |
line wrap: on
line diff
--- a/plugins/libcalendaring/composer.json Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,30 +0,0 @@ -{ - "name": "kolab/libcalendaring", - "type": "roundcube-plugin", - "description": "Library providing common functions for calendaring plugins", - "homepage": "https://git.kolab.org/diffusion/RPK/", - "license": "AGPLv3", - "authors": [ - { - "name": "Alensader Machniak", - "email": "machniak@kolabsys.com", - "role": "Lead" - } - ], - "repositories": [ - { - "type": "composer", - "url": "https://plugins.roundcube.net" - } - ], - "require": { - "php": ">=5.4.0", - "roundcube/plugin-installer": ">=0.1.3", - "sabre/vobject": "~3.3.3" - }, - "extra": { - "roundcube": { - "min-version": "1.3.0" - } - } -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Component.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,405 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * VObject Component - * - * This class represents a VCALENDAR/VCARD component. A component is for example - * VEVENT, VTODO and also VCALENDAR. It starts with BEGIN:COMPONENTNAME and - * ends with END:COMPONENTNAME - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class Component extends Node { - - /** - * Name, for example VEVENT - * - * @var string - */ - public $name; - - /** - * Children properties and components - * - * @var array - */ - public $children = array(); - - /** - * If components are added to this map, they will be automatically mapped - * to their respective classes, if parsed by the reader or constructed with - * the 'create' method. - * - * @var array - */ - static public $classMap = array( - 'VALARM' => 'Sabre\\VObject\\Component\\VAlarm', - 'VCALENDAR' => 'Sabre\\VObject\\Component\\VCalendar', - 'VCARD' => 'Sabre\\VObject\\Component\\VCard', - 'VEVENT' => 'Sabre\\VObject\\Component\\VEvent', - 'VJOURNAL' => 'Sabre\\VObject\\Component\\VJournal', - 'VTODO' => 'Sabre\\VObject\\Component\\VTodo', - 'VFREEBUSY' => 'Sabre\\VObject\\Component\\VFreeBusy', - ); - - /** - * Creates the new component by name, but in addition will also see if - * there's a class mapped to the property name. - * - * @param string $name - * @param string $value - * @return Component - */ - static public function create($name, $value = null) { - - $name = strtoupper($name); - - if (isset(self::$classMap[$name])) { - return new self::$classMap[$name]($name, $value); - } else { - return new self($name, $value); - } - - } - - /** - * Creates a new component. - * - * By default this object will iterate over its own children, but this can - * be overridden with the iterator argument - * - * @param string $name - * @param ElementList $iterator - */ - public function __construct($name, ElementList $iterator = null) { - - $this->name = strtoupper($name); - if (!is_null($iterator)) $this->iterator = $iterator; - - } - - /** - * Turns the object back into a serialized blob. - * - * @return string - */ - public function serialize() { - - $str = "BEGIN:" . $this->name . "\r\n"; - - /** - * Gives a component a 'score' for sorting purposes. - * - * This is solely used by the childrenSort method. - * - * A higher score means the item will be lower in the list. - * To avoid score collisions, each "score category" has a reasonable - * space to accomodate elements. The $key is added to the $score to - * preserve the original relative order of elements. - * - * @param int $key - * @param array $array - * @return int - */ - $sortScore = function($key, $array) { - - if ($array[$key] instanceof Component) { - - // We want to encode VTIMEZONE first, this is a personal - // preference. - if ($array[$key]->name === 'VTIMEZONE') { - $score=300000000; - return $score+$key; - } else { - $score=400000000; - return $score+$key; - } - } else { - // Properties get encoded first - // VCARD version 4.0 wants the VERSION property to appear first - if ($array[$key] instanceof Property) { - if ($array[$key]->name === 'VERSION') { - $score=100000000; - return $score+$key; - } else { - // All other properties - $score=200000000; - return $score+$key; - } - } - } - - }; - - $tmp = $this->children; - uksort($this->children, function($a, $b) use ($sortScore, $tmp) { - - $sA = $sortScore($a, $tmp); - $sB = $sortScore($b, $tmp); - - if ($sA === $sB) return 0; - - return ($sA < $sB) ? -1 : 1; - - }); - - foreach($this->children as $child) $str.=$child->serialize(); - $str.= "END:" . $this->name . "\r\n"; - - return $str; - - } - - /** - * Adds a new component or element - * - * You can call this method with the following syntaxes: - * - * add(Node $node) - * add(string $name, $value, array $parameters = array()) - * - * The first version adds an Element - * The second adds a property as a string. - * - * @param mixed $item - * @param mixed $itemValue - * @return void - */ - public function add($item, $itemValue = null, array $parameters = array()) { - - if ($item instanceof Node) { - if (!is_null($itemValue)) { - throw new \InvalidArgumentException('The second argument must not be specified, when passing a VObject Node'); - } - $item->parent = $this; - $this->children[] = $item; - } elseif(is_string($item)) { - - $item = Property::create($item,$itemValue, $parameters); - $item->parent = $this; - $this->children[] = $item; - - } else { - - throw new \InvalidArgumentException('The first argument must either be a \\Sabre\\VObject\\Node or a string'); - - } - - } - - /** - * Returns an iterable list of children - * - * @return ElementList - */ - public function children() { - - return new ElementList($this->children); - - } - - /** - * Returns an array with elements that match the specified name. - * - * This function is also aware of MIME-Directory groups (as they appear in - * vcards). This means that if a property is grouped as "HOME.EMAIL", it - * will also be returned when searching for just "EMAIL". If you want to - * search for a property in a specific group, you can select on the entire - * string ("HOME.EMAIL"). If you want to search on a specific property that - * has not been assigned a group, specify ".EMAIL". - * - * Keys are retained from the 'children' array, which may be confusing in - * certain cases. - * - * @param string $name - * @return array - */ - public function select($name) { - - $group = null; - $name = strtoupper($name); - if (strpos($name,'.')!==false) { - list($group,$name) = explode('.', $name, 2); - } - - $result = array(); - foreach($this->children as $key=>$child) { - - if ( - strtoupper($child->name) === $name && - (is_null($group) || ( $child instanceof Property && strtoupper($child->group) === $group)) - ) { - - $result[$key] = $child; - - } - } - - reset($result); - return $result; - - } - - /** - * This method only returns a list of sub-components. Properties are - * ignored. - * - * @return array - */ - public function getComponents() { - - $result = array(); - foreach($this->children as $child) { - if ($child instanceof Component) { - $result[] = $child; - } - } - - return $result; - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * - Node::REPAIR - If something is broken, and automatic repair may - * be attempted. - * - * An array is returned with warnings. - * - * Every item in the array has the following properties: - * * level - (number between 1 and 3 with severity information) - * * message - (human readable message) - * * node - (reference to the offending node) - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - $result = array(); - foreach($this->children as $child) { - $result = array_merge($result, $child->validate($options)); - } - return $result; - - } - - /* Magic property accessors {{{ */ - - /** - * Using 'get' you will either get a property or component, - * - * If there were no child-elements found with the specified name, - * null is returned. - * - * @param string $name - * @return Property - */ - public function __get($name) { - - $matches = $this->select($name); - if (count($matches)===0) { - return null; - } else { - $firstMatch = current($matches); - /** @var $firstMatch Property */ - $firstMatch->setIterator(new ElementList(array_values($matches))); - return $firstMatch; - } - - } - - /** - * This method checks if a sub-element with the specified name exists. - * - * @param string $name - * @return bool - */ - public function __isset($name) { - - $matches = $this->select($name); - return count($matches)>0; - - } - - /** - * Using the setter method you can add properties or subcomponents - * - * You can either pass a Component, Property - * object, or a string to automatically create a Property. - * - * If the item already exists, it will be removed. If you want to add - * a new item with the same name, always use the add() method. - * - * @param string $name - * @param mixed $value - * @return void - */ - public function __set($name, $value) { - - $matches = $this->select($name); - $overWrite = count($matches)?key($matches):null; - - if ($value instanceof Component || $value instanceof Property) { - $value->parent = $this; - if (!is_null($overWrite)) { - $this->children[$overWrite] = $value; - } else { - $this->children[] = $value; - } - } elseif (is_scalar($value)) { - $property = Property::create($name,$value); - $property->parent = $this; - if (!is_null($overWrite)) { - $this->children[$overWrite] = $property; - } else { - $this->children[] = $property; - } - } else { - throw new \InvalidArgumentException('You must pass a \\Sabre\\VObject\\Component, \\Sabre\\VObject\\Property or scalar type'); - } - - } - - /** - * Removes all properties and components within this component. - * - * @param string $name - * @return void - */ - public function __unset($name) { - - $matches = $this->select($name); - foreach($matches as $k=>$child) { - - unset($this->children[$k]); - $child->parent = null; - - } - - } - - /* }}} */ - - /** - * This method is automatically called when the object is cloned. - * Specifically, this will ensure all child elements are also cloned. - * - * @return void - */ - public function __clone() { - - foreach($this->children as $key=>$child) { - $this->children[$key] = clone $child; - $this->children[$key]->parent = $this; - } - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Component/VAlarm.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,108 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; -use Sabre\VObject; - -/** - * VAlarm component - * - * This component contains some additional functionality specific for VALARMs. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class VAlarm extends VObject\Component { - - /** - * Returns a DateTime object when this alarm is going to trigger. - * - * This ignores repeated alarm, only the first trigger is returned. - * - * @return DateTime - */ - public function getEffectiveTriggerTime() { - - $trigger = $this->TRIGGER; - if(!isset($trigger['VALUE']) || strtoupper($trigger['VALUE']) === 'DURATION') { - $triggerDuration = VObject\DateTimeParser::parseDuration($this->TRIGGER); - $related = (isset($trigger['RELATED']) && strtoupper($trigger['RELATED']) == 'END') ? 'END' : 'START'; - - $parentComponent = $this->parent; - if ($related === 'START') { - - if ($parentComponent->name === 'VTODO') { - $propName = 'DUE'; - } else { - $propName = 'DTSTART'; - } - - $effectiveTrigger = clone $parentComponent->$propName->getDateTime(); - $effectiveTrigger->add($triggerDuration); - } else { - if ($parentComponent->name === 'VTODO') { - $endProp = 'DUE'; - } elseif ($parentComponent->name === 'VEVENT') { - $endProp = 'DTEND'; - } else { - throw new \LogicException('time-range filters on VALARM components are only supported when they are a child of VTODO or VEVENT'); - } - - if (isset($parentComponent->$endProp)) { - $effectiveTrigger = clone $parentComponent->$endProp->getDateTime(); - $effectiveTrigger->add($triggerDuration); - } elseif (isset($parentComponent->DURATION)) { - $effectiveTrigger = clone $parentComponent->DTSTART->getDateTime(); - $duration = VObject\DateTimeParser::parseDuration($parentComponent->DURATION); - $effectiveTrigger->add($duration); - $effectiveTrigger->add($triggerDuration); - } else { - $effectiveTrigger = clone $parentComponent->DTSTART->getDateTime(); - $effectiveTrigger->add($triggerDuration); - } - } - } else { - $effectiveTrigger = $trigger->getDateTime(); - } - return $effectiveTrigger; - - } - - /** - * Returns true or false depending on if the event falls in the specified - * time-range. This is used for filtering purposes. - * - * The rules used to determine if an event falls within the specified - * time-range is based on the CalDAV specification. - * - * @param \DateTime $start - * @param \DateTime $end - * @return bool - */ - public function isInTimeRange(\DateTime $start, \DateTime $end) { - - $effectiveTrigger = $this->getEffectiveTriggerTime(); - - if (isset($this->DURATION)) { - $duration = VObject\DateTimeParser::parseDuration($this->DURATION); - $repeat = (string)$this->repeat; - if (!$repeat) { - $repeat = 1; - } - - $period = new \DatePeriod($effectiveTrigger, $duration, (int)$repeat); - - foreach($period as $occurrence) { - - if ($start <= $occurrence && $end > $occurrence) { - return true; - } - } - return false; - } else { - return ($start <= $effectiveTrigger && $end > $effectiveTrigger); - } - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Component/VCalendar.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,244 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -/** - * The VCalendar component - * - * This component adds functionality to a component, specific for a VCALENDAR. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class VCalendar extends VObject\Document { - - static $defaultName = 'VCALENDAR'; - - /** - * Returns a list of all 'base components'. For instance, if an Event has - * a recurrence rule, and one instance is overridden, the overridden event - * will have the same UID, but will be excluded from this list. - * - * VTIMEZONE components will always be excluded. - * - * @param string $componentName filter by component name - * @return array - */ - public function getBaseComponents($componentName = null) { - - $components = array(); - foreach($this->children as $component) { - - if (!$component instanceof VObject\Component) - continue; - - if (isset($component->{'RECURRENCE-ID'})) - continue; - - if ($componentName && $component->name !== strtoupper($componentName)) - continue; - - if ($component->name === 'VTIMEZONE') - continue; - - $components[] = $component; - - } - - return $components; - - } - - /** - * If this calendar object, has events with recurrence rules, this method - * can be used to expand the event into multiple sub-events. - * - * Each event will be stripped from it's recurrence information, and only - * the instances of the event in the specified timerange will be left - * alone. - * - * In addition, this method will cause timezone information to be stripped, - * and normalized to UTC. - * - * This method will alter the VCalendar. This cannot be reversed. - * - * This functionality is specifically used by the CalDAV standard. It is - * possible for clients to request expand events, if they are rather simple - * clients and do not have the possibility to calculate recurrences. - * - * @param DateTime $start - * @param DateTime $end - * @return void - */ - public function expand(\DateTime $start, \DateTime $end) { - - $newEvents = array(); - - foreach($this->select('VEVENT') as $key=>$vevent) { - - if (isset($vevent->{'RECURRENCE-ID'})) { - unset($this->children[$key]); - continue; - } - - - if (!$vevent->rrule) { - unset($this->children[$key]); - if ($vevent->isInTimeRange($start, $end)) { - $newEvents[] = $vevent; - } - continue; - } - - $uid = (string)$vevent->uid; - if (!$uid) { - throw new \LogicException('Event did not have a UID!'); - } - - $it = new VObject\RecurrenceIterator($this, $vevent->uid); - $it->fastForward($start); - - while($it->valid() && $it->getDTStart() < $end) { - - if ($it->getDTEnd() > $start) { - - $newEvents[] = $it->getEventObject(); - - } - $it->next(); - - } - unset($this->children[$key]); - - } - - foreach($newEvents as $newEvent) { - - foreach($newEvent->children as $child) { - if ($child instanceof VObject\Property\DateTime && - $child->getDateType() == VObject\Property\DateTime::LOCALTZ) { - $child->setDateTime($child->getDateTime(),VObject\Property\DateTime::UTC); - } - } - - $this->add($newEvent); - - } - - // Removing all VTIMEZONE components - unset($this->VTIMEZONE); - - } - - /** - * Validates the node for correctness. - * An array is returned with warnings. - * - * Every item in the array has the following properties: - * * level - (number between 1 and 3 with severity information) - * * message - (human readable message) - * * node - (reference to the offending node) - * - * @return array - */ - /* - public function validate() { - - $warnings = array(); - - $version = $this->select('VERSION'); - if (count($version)!==1) { - $warnings[] = array( - 'level' => 1, - 'message' => 'The VERSION property must appear in the VCALENDAR component exactly 1 time', - 'node' => $this, - ); - } else { - if ((string)$this->VERSION !== '2.0') { - $warnings[] = array( - 'level' => 1, - 'message' => 'Only iCalendar version 2.0 as defined in rfc5545 is supported.', - 'node' => $this, - ); - } - } - $version = $this->select('PRODID'); - if (count($version)!==1) { - $warnings[] = array( - 'level' => 2, - 'message' => 'The PRODID property must appear in the VCALENDAR component exactly 1 time', - 'node' => $this, - ); - } - if (count($this->CALSCALE) > 1) { - $warnings[] = array( - 'level' => 2, - 'message' => 'The CALSCALE property must not be specified more than once.', - 'node' => $this, - ); - } - if (count($this->METHOD) > 1) { - $warnings[] = array( - 'level' => 2, - 'message' => 'The METHOD property must not be specified more than once.', - 'node' => $this, - ); - } - - $allowedComponents = array( - 'VEVENT', - 'VTODO', - 'VJOURNAL', - 'VFREEBUSY', - 'VTIMEZONE', - ); - $allowedProperties = array( - 'PRODID', - 'VERSION', - 'CALSCALE', - 'METHOD', - ); - $componentsFound = 0; - foreach($this->children as $child) { - if($child instanceof Component) { - $componentsFound++; - if (!in_array($child->name, $allowedComponents)) { - $warnings[] = array( - 'level' => 1, - 'message' => 'The ' . $child->name . " component is not allowed in the VCALENDAR component", - 'node' => $this, - ); - } - } - if ($child instanceof Property) { - if (!in_array($child->name, $allowedProperties)) { - $warnings[] = array( - 'level' => 2, - 'message' => 'The ' . $child->name . " property is not allowed in the VCALENDAR component", - 'node' => $this, - ); - } - } - } - - if ($componentsFound===0) { - $warnings[] = array( - 'level' => 1, - 'message' => 'An iCalendar object must have at least 1 component.', - 'node' => $this, - ); - } - - return array_merge( - $warnings, - parent::validate() - ); - - } - */ - -} -
--- a/plugins/libcalendaring/lib/Sabre/VObject/Component/VCard.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,107 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -/** - * The VCard component - * - * This component represents the BEGIN:VCARD and END:VCARD found in every - * vcard. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class VCard extends VObject\Component { - - static $defaultName = 'VCARD'; - - /** - * VCards with version 2.1, 3.0 and 4.0 are found. - * - * If the VCARD doesn't know its version, 4.0 is assumed. - */ - const DEFAULT_VERSION = '4.0'; - - /** - * Validates the node for correctness. - * - * The following options are supported: - * - Node::REPAIR - If something is broken, and automatic repair may - * be attempted. - * - * An array is returned with warnings. - * - * Every item in the array has the following properties: - * * level - (number between 1 and 3 with severity information) - * * message - (human readable message) - * * node - (reference to the offending node) - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - $warnings = array(); - - $version = $this->select('VERSION'); - if (count($version)!==1) { - $warnings[] = array( - 'level' => 1, - 'message' => 'The VERSION property must appear in the VCARD component exactly 1 time', - 'node' => $this, - ); - if ($options & self::REPAIR) { - $this->VERSION = self::DEFAULT_VERSION; - } - } else { - $version = (string)$this->VERSION; - if ($version!=='2.1' && $version!=='3.0' && $version!=='4.0') { - $warnings[] = array( - 'level' => 1, - 'message' => 'Only vcard version 4.0 (RFC6350), version 3.0 (RFC2426) or version 2.1 (icm-vcard-2.1) are supported.', - 'node' => $this, - ); - if ($options & self::REPAIR) { - $this->VERSION = '4.0'; - } - } - - } - $fn = $this->select('FN'); - if (count($fn)!==1) { - $warnings[] = array( - 'level' => 1, - 'message' => 'The FN property must appear in the VCARD component exactly 1 time', - 'node' => $this, - ); - if (($options & self::REPAIR) && count($fn) === 0) { - // We're going to try to see if we can use the contents of the - // N property. - if (isset($this->N)) { - $value = explode(';', (string)$this->N); - if (isset($value[1]) && $value[1]) { - $this->FN = $value[1] . ' ' . $value[0]; - } else { - $this->FN = $value[0]; - } - - // Otherwise, the ORG property may work - } elseif (isset($this->ORG)) { - $this->FN = (string)$this->ORG; - } - - } - } - - return array_merge( - parent::validate($options), - $warnings - ); - - } - -} -
--- a/plugins/libcalendaring/lib/Sabre/VObject/Component/VEvent.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,70 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; -use Sabre\VObject; - -/** - * VEvent component - * - * This component contains some additional functionality specific for VEVENT's. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class VEvent extends VObject\Component { - - /** - * Returns true or false depending on if the event falls in the specified - * time-range. This is used for filtering purposes. - * - * The rules used to determine if an event falls within the specified - * time-range is based on the CalDAV specification. - * - * @param \DateTime $start - * @param \DateTime $end - * @return bool - */ - public function isInTimeRange(\DateTime $start, \DateTime $end) { - - if ($this->RRULE) { - $it = new VObject\RecurrenceIterator($this); - $it->fastForward($start); - - // We fast-forwarded to a spot where the end-time of the - // recurrence instance exceeded the start of the requested - // time-range. - // - // If the starttime of the recurrence did not exceed the - // end of the time range as well, we have a match. - return ($it->getDTStart() < $end && $it->getDTEnd() > $start); - - } - - $effectiveStart = $this->DTSTART->getDateTime(); - if (isset($this->DTEND)) { - - // The DTEND property is considered non inclusive. So for a 3 day - // event in july, dtstart and dtend would have to be July 1st and - // July 4th respectively. - // - // See: - // http://tools.ietf.org/html/rfc5545#page-54 - $effectiveEnd = $this->DTEND->getDateTime(); - - } elseif (isset($this->DURATION)) { - $effectiveEnd = clone $effectiveStart; - $effectiveEnd->add( VObject\DateTimeParser::parseDuration($this->DURATION) ); - } elseif ($this->DTSTART->getDateType() == VObject\Property\DateTime::DATE) { - $effectiveEnd = clone $effectiveStart; - $effectiveEnd->modify('+1 day'); - } else { - $effectiveEnd = clone $effectiveStart; - } - return ( - ($start <= $effectiveEnd) && ($end > $effectiveStart) - ); - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Component/VFreeBusy.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,68 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -/** - * The VFreeBusy component - * - * This component adds functionality to a component, specific for VFREEBUSY - * components. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class VFreeBusy extends VObject\Component { - - /** - * Checks based on the contained FREEBUSY information, if a timeslot is - * available. - * - * @param DateTime $start - * @param Datetime $end - * @return bool - */ - public function isFree(\DateTime $start, \Datetime $end) { - - foreach($this->select('FREEBUSY') as $freebusy) { - - // We are only interested in FBTYPE=BUSY (the default), - // FBTYPE=BUSY-TENTATIVE or FBTYPE=BUSY-UNAVAILABLE. - if (isset($freebusy['FBTYPE']) && strtoupper(substr((string)$freebusy['FBTYPE'],0,4))!=='BUSY') { - continue; - } - - // The freebusy component can hold more than 1 value, separated by - // commas. - $periods = explode(',', (string)$freebusy); - - foreach($periods as $period) { - // Every period is formatted as [start]/[end]. The start is an - // absolute UTC time, the end may be an absolute UTC time, or - // duration (relative) value. - list($busyStart, $busyEnd) = explode('/', $period); - - $busyStart = VObject\DateTimeParser::parse($busyStart); - $busyEnd = VObject\DateTimeParser::parse($busyEnd); - if ($busyEnd instanceof \DateInterval) { - $tmp = clone $busyStart; - $tmp->add($busyEnd); - $busyEnd = $tmp; - } - - if($start < $busyEnd && $end > $busyStart) { - return false; - } - - } - - } - - return true; - - } - -} -
--- a/plugins/libcalendaring/lib/Sabre/VObject/Component/VJournal.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,46 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -/** - * VJournal component - * - * This component contains some additional functionality specific for VJOURNALs. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class VJournal extends VObject\Component { - - /** - * Returns true or false depending on if the event falls in the specified - * time-range. This is used for filtering purposes. - * - * The rules used to determine if an event falls within the specified - * time-range is based on the CalDAV specification. - * - * @param DateTime $start - * @param DateTime $end - * @return bool - */ - public function isInTimeRange(\DateTime $start, \DateTime $end) { - - $dtstart = isset($this->DTSTART)?$this->DTSTART->getDateTime():null; - if ($dtstart) { - $effectiveEnd = clone $dtstart; - if ($this->DTSTART->getDateType() == VObject\Property\DateTime::DATE) { - $effectiveEnd->modify('+1 day'); - } - - return ($start <= $effectiveEnd && $end > $dtstart); - - } - return false; - - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Component/VTodo.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,68 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -/** - * VTodo component - * - * This component contains some additional functionality specific for VTODOs. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class VTodo extends VObject\Component { - - /** - * Returns true or false depending on if the event falls in the specified - * time-range. This is used for filtering purposes. - * - * The rules used to determine if an event falls within the specified - * time-range is based on the CalDAV specification. - * - * @param DateTime $start - * @param DateTime $end - * @return bool - */ - public function isInTimeRange(\DateTime $start, \DateTime $end) { - - $dtstart = isset($this->DTSTART)?$this->DTSTART->getDateTime():null; - $duration = isset($this->DURATION)?VObject\DateTimeParser::parseDuration($this->DURATION):null; - $due = isset($this->DUE)?$this->DUE->getDateTime():null; - $completed = isset($this->COMPLETED)?$this->COMPLETED->getDateTime():null; - $created = isset($this->CREATED)?$this->CREATED->getDateTime():null; - - if ($dtstart) { - if ($duration) { - $effectiveEnd = clone $dtstart; - $effectiveEnd->add($duration); - return $start <= $effectiveEnd && $end > $dtstart; - } elseif ($due) { - return - ($start < $due || $start <= $dtstart) && - ($end > $dtstart || $end >= $due); - } else { - return $start <= $dtstart && $end > $dtstart; - } - } - if ($due) { - return ($start < $due && $end >= $due); - } - if ($completed && $created) { - return - ($start <= $created || $start <= $completed) && - ($end >= $created || $end >= $completed); - } - if ($completed) { - return ($start <= $completed && $end >= $completed); - } - if ($created) { - return ($end > $created); - } - return true; - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/DateTimeParser.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,181 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * DateTimeParser - * - * This class is responsible for parsing the several different date and time - * formats iCalendar and vCards have. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class DateTimeParser { - - /** - * Parses an iCalendar (rfc5545) formatted datetime and returns a DateTime object - * - * Specifying a reference timezone is optional. It will only be used - * if the non-UTC format is used. The argument is used as a reference, the - * returned DateTime object will still be in the UTC timezone. - * - * @param string $dt - * @param DateTimeZone $tz - * @return DateTime - */ - static public function parseDateTime($dt,\DateTimeZone $tz = null) { - - // Format is YYYYMMDD + "T" + hhmmss - $result = preg_match('/^([1-4][0-9]{3})([0-1][0-9])([0-3][0-9])T([0-2][0-9])([0-5][0-9])([0-5][0-9])([Z]?)$/',$dt,$matches); - - if (!$result) { - throw new \LogicException('The supplied iCalendar datetime value is incorrect: ' . $dt); - } - - if ($matches[7]==='Z' || is_null($tz)) { - $tz = new \DateTimeZone('UTC'); - } - $date = new \DateTime($matches[1] . '-' . $matches[2] . '-' . $matches[3] . ' ' . $matches[4] . ':' . $matches[5] .':' . $matches[6], $tz); - - // Still resetting the timezone, to normalize everything to UTC - $date->setTimeZone(new \DateTimeZone('UTC')); - return $date; - - } - - /** - * Parses an iCalendar (rfc5545) formatted date and returns a DateTime object - * - * @param string $date - * @return DateTime - */ - static public function parseDate($date) { - - // Format is YYYYMMDD - $result = preg_match('/^([1-4][0-9]{3})([0-1][0-9])([0-3][0-9])$/',$date,$matches); - - if (!$result) { - throw new \LogicException('The supplied iCalendar date value is incorrect: ' . $date); - } - - $date = new \DateTime($matches[1] . '-' . $matches[2] . '-' . $matches[3], new \DateTimeZone('UTC')); - return $date; - - } - - /** - * Parses an iCalendar (RFC5545) formatted duration value. - * - * This method will either return a DateTimeInterval object, or a string - * suitable for strtotime or DateTime::modify. - * - * @param string $duration - * @param bool $asString - * @return DateInterval|string - */ - static public function parseDuration($duration, $asString = false) { - - $result = preg_match('/^(?P<plusminus>\+|-)?P((?P<week>\d+)W)?((?P<day>\d+)D)?(T((?P<hour>\d+)H)?((?P<minute>\d+)M)?((?P<second>\d+)S)?)?$/', $duration, $matches); - if (!$result) { - throw new \LogicException('The supplied iCalendar duration value is incorrect: ' . $duration); - } - - if (!$asString) { - $invert = false; - if ($matches['plusminus']==='-') { - $invert = true; - } - - - $parts = array( - 'week', - 'day', - 'hour', - 'minute', - 'second', - ); - foreach($parts as $part) { - $matches[$part] = isset($matches[$part])&&$matches[$part]?(int)$matches[$part]:0; - } - - - // We need to re-construct the $duration string, because weeks and - // days are not supported by DateInterval in the same string. - $duration = 'P'; - $days = $matches['day']; - if ($matches['week']) { - $days+=$matches['week']*7; - } - if ($days) - $duration.=$days . 'D'; - - if ($matches['minute'] || $matches['second'] || $matches['hour']) { - $duration.='T'; - - if ($matches['hour']) - $duration.=$matches['hour'].'H'; - - if ($matches['minute']) - $duration.=$matches['minute'].'M'; - - if ($matches['second']) - $duration.=$matches['second'].'S'; - - } - - if ($duration==='P') { - $duration = 'PT0S'; - } - $iv = new \DateInterval($duration); - if ($invert) $iv->invert = true; - - return $iv; - - } - - - - $parts = array( - 'week', - 'day', - 'hour', - 'minute', - 'second', - ); - - $newDur = ''; - foreach($parts as $part) { - if (isset($matches[$part]) && $matches[$part]) { - $newDur.=' '.$matches[$part] . ' ' . $part . 's'; - } - } - - $newDur = ($matches['plusminus']==='-'?'-':'+') . trim($newDur); - if ($newDur === '+') { $newDur = '+0 seconds'; }; - return $newDur; - - } - - /** - * Parses either a Date or DateTime, or Duration value. - * - * @param string $date - * @param DateTimeZone|string $referenceTZ - * @return DateTime|DateInterval - */ - static public function parse($date, $referenceTZ = null) { - - if ($date[0]==='P' || ($date[0]==='-' && $date[1]==='P')) { - return self::parseDuration($date); - } elseif (strlen($date)===8) { - return self::parseDate($date); - } else { - return self::parseDateTime($date, $referenceTZ); - } - - } - - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Document.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,109 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Document - * - * A document is just like a component, except that it's also the top level - * element. - * - * Both a VCALENDAR and a VCARD are considered documents. - * - * This class also provides a registry for document types. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH. All rights reserved. - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -abstract class Document extends Component { - - /** - * The default name for this component. - * - * This should be 'VCALENDAR' or 'VCARD'. - * - * @var string - */ - static $defaultName; - - /** - * Creates a new document. - * - * We're changing the default behavior slightly here. First, we don't want - * to have to specify a name (we already know it), and we want to allow - * children to be specified in the first argument. - * - * But, the default behavior also works. - * - * So the two sigs: - * - * new Document(array $children = array()); - * new Document(string $name, array $children = array()) - * - * @return void - */ - public function __construct() { - - $args = func_get_args(); - if (count($args)===0 || is_array($args[0])) { - array_unshift($args, static::$defaultName); - call_user_func_array(array('parent', '__construct'), $args); - } else { - call_user_func_array(array('parent', '__construct'), $args); - } - - } - - /** - * Creates a new component - * - * This method automatically searches for the correct component class, based - * on its name. - * - * You can specify the children either in key=>value syntax, in which case - * properties will automatically be created, or you can just pass a list of - * Component and Property object. - * - * @param string $name - * @param array $children - * @return Component - */ - public function createComponent($name, array $children = array()) { - - $component = Component::create($name); - foreach($children as $k=>$v) { - - if ($v instanceof Node) { - $component->add($v); - } else { - $component->add($k, $v); - } - - } - return $component; - - } - - /** - * Factory method for creating new properties - * - * This method automatically searches for the correct property class, based - * on its name. - * - * You can specify the parameters either in key=>value syntax, in which case - * parameters will automatically be created, or you can just pass a list of - * Parameter objects. - * - * @param string $name - * @param mixed $value - * @param array $parameters - * @return Property - */ - public function createProperty($name, $value = null, array $parameters = array()) { - - return Property::create($name, $value, $parameters); - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/ElementList.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,172 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * VObject ElementList - * - * This class represents a list of elements. Lists are the result of queries, - * such as doing $vcalendar->vevent where there's multiple VEVENT objects. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class ElementList implements \Iterator, \Countable, \ArrayAccess { - - /** - * Inner elements - * - * @var array - */ - protected $elements = array(); - - /** - * Creates the element list. - * - * @param array $elements - */ - public function __construct(array $elements) { - - $this->elements = $elements; - - } - - /* {{{ Iterator interface */ - - /** - * Current position - * - * @var int - */ - private $key = 0; - - /** - * Returns current item in iteration - * - * @return Element - */ - public function current() { - - return $this->elements[$this->key]; - - } - - /** - * To the next item in the iterator - * - * @return void - */ - public function next() { - - $this->key++; - - } - - /** - * Returns the current iterator key - * - * @return int - */ - public function key() { - - return $this->key; - - } - - /** - * Returns true if the current position in the iterator is a valid one - * - * @return bool - */ - public function valid() { - - return isset($this->elements[$this->key]); - - } - - /** - * Rewinds the iterator - * - * @return void - */ - public function rewind() { - - $this->key = 0; - - } - - /* }}} */ - - /* {{{ Countable interface */ - - /** - * Returns the number of elements - * - * @return int - */ - public function count() { - - return count($this->elements); - - } - - /* }}} */ - - /* {{{ ArrayAccess Interface */ - - - /** - * Checks if an item exists through ArrayAccess. - * - * @param int $offset - * @return bool - */ - public function offsetExists($offset) { - - return isset($this->elements[$offset]); - - } - - /** - * Gets an item through ArrayAccess. - * - * @param int $offset - * @return mixed - */ - public function offsetGet($offset) { - - return $this->elements[$offset]; - - } - - /** - * Sets an item through ArrayAccess. - * - * @param int $offset - * @param mixed $value - * @return void - */ - public function offsetSet($offset,$value) { - - throw new \LogicException('You can not add new objects to an ElementList'); - - } - - /** - * Sets an item through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @return void - */ - public function offsetUnset($offset) { - - throw new \LogicException('You can not remove objects from an ElementList'); - - } - - /* }}} */ - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/FreeBusyGenerator.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,322 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * This class helps with generating FREEBUSY reports based on existing sets of - * objects. - * - * It only looks at VEVENT and VFREEBUSY objects from the sourcedata, and - * generates a single VFREEBUSY object. - * - * VFREEBUSY components are described in RFC5545, The rules for what should - * go in a single freebusy report is taken from RFC4791, section 7.10. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class FreeBusyGenerator { - - /** - * Input objects - * - * @var array - */ - protected $objects; - - /** - * Start of range - * - * @var DateTime|null - */ - protected $start; - - /** - * End of range - * - * @var DateTime|null - */ - protected $end; - - /** - * VCALENDAR object - * - * @var Component - */ - protected $baseObject; - - /** - * Creates the generator. - * - * Check the setTimeRange and setObjects methods for details about the - * arguments. - * - * @param DateTime $start - * @param DateTime $end - * @param mixed $objects - * @return void - */ - public function __construct(\DateTime $start = null, \DateTime $end = null, $objects = null) { - - if ($start && $end) { - $this->setTimeRange($start, $end); - } - - if ($objects) { - $this->setObjects($objects); - } - - } - - /** - * Sets the VCALENDAR object. - * - * If this is set, it will not be generated for you. You are responsible - * for setting things like the METHOD, CALSCALE, VERSION, etc.. - * - * The VFREEBUSY object will be automatically added though. - * - * @param Component $vcalendar - * @return void - */ - public function setBaseObject(Component $vcalendar) { - - $this->baseObject = $vcalendar; - - } - - /** - * Sets the input objects - * - * You must either specify a valendar object as a strong, or as the parse - * Component. - * It's also possible to specify multiple objects as an array. - * - * @param mixed $objects - * @return void - */ - public function setObjects($objects) { - - if (!is_array($objects)) { - $objects = array($objects); - } - - $this->objects = array(); - foreach($objects as $object) { - - if (is_string($object)) { - $this->objects[] = Reader::read($object); - } elseif ($object instanceof Component) { - $this->objects[] = $object; - } else { - throw new \InvalidArgumentException('You can only pass strings or \\Sabre\\VObject\\Component arguments to setObjects'); - } - - } - - } - - /** - * Sets the time range - * - * Any freebusy object falling outside of this time range will be ignored. - * - * @param DateTime $start - * @param DateTime $end - * @return void - */ - public function setTimeRange(\DateTime $start = null, \DateTime $end = null) { - - $this->start = $start; - $this->end = $end; - - } - - /** - * Parses the input data and returns a correct VFREEBUSY object, wrapped in - * a VCALENDAR. - * - * @return Component - */ - public function getResult() { - - $busyTimes = array(); - - foreach($this->objects as $object) { - - foreach($object->getBaseComponents() as $component) { - - switch($component->name) { - - case 'VEVENT' : - - $FBTYPE = 'BUSY'; - if (isset($component->TRANSP) && (strtoupper($component->TRANSP) === 'TRANSPARENT')) { - break; - } - if (isset($component->STATUS)) { - $status = strtoupper($component->STATUS); - if ($status==='CANCELLED') { - break; - } - if ($status==='TENTATIVE') { - $FBTYPE = 'BUSY-TENTATIVE'; - } - } - - $times = array(); - - if ($component->RRULE) { - - $iterator = new RecurrenceIterator($object, (string)$component->uid); - if ($this->start) { - $iterator->fastForward($this->start); - } - - $maxRecurrences = 200; - - while($iterator->valid() && --$maxRecurrences) { - - $startTime = $iterator->getDTStart(); - if ($this->end && $startTime > $this->end) { - break; - } - $times[] = array( - $iterator->getDTStart(), - $iterator->getDTEnd(), - ); - - $iterator->next(); - - } - - } else { - - $startTime = $component->DTSTART->getDateTime(); - if ($this->end && $startTime > $this->end) { - break; - } - $endTime = null; - if (isset($component->DTEND)) { - $endTime = $component->DTEND->getDateTime(); - } elseif (isset($component->DURATION)) { - $duration = DateTimeParser::parseDuration((string)$component->DURATION); - $endTime = clone $startTime; - $endTime->add($duration); - } elseif ($component->DTSTART->getDateType() === Property\DateTime::DATE) { - $endTime = clone $startTime; - $endTime->modify('+1 day'); - } else { - // The event had no duration (0 seconds) - break; - } - - $times[] = array($startTime, $endTime); - - } - - foreach($times as $time) { - - if ($this->end && $time[0] > $this->end) break; - if ($this->start && $time[1] < $this->start) break; - - $busyTimes[] = array( - $time[0], - $time[1], - $FBTYPE, - ); - } - break; - - case 'VFREEBUSY' : - foreach($component->FREEBUSY as $freebusy) { - - $fbType = isset($freebusy['FBTYPE'])?strtoupper($freebusy['FBTYPE']):'BUSY'; - - // Skipping intervals marked as 'free' - if ($fbType==='FREE') - continue; - - $values = explode(',', $freebusy); - foreach($values as $value) { - list($startTime, $endTime) = explode('/', $value); - $startTime = DateTimeParser::parseDateTime($startTime); - - if (substr($endTime,0,1)==='P' || substr($endTime,0,2)==='-P') { - $duration = DateTimeParser::parseDuration($endTime); - $endTime = clone $startTime; - $endTime->add($duration); - } else { - $endTime = DateTimeParser::parseDateTime($endTime); - } - - if($this->start && $this->start > $endTime) continue; - if($this->end && $this->end < $startTime) continue; - $busyTimes[] = array( - $startTime, - $endTime, - $fbType - ); - - } - - - } - break; - - - - } - - - } - - } - - if ($this->baseObject) { - $calendar = $this->baseObject; - } else { - $calendar = Component::create('VCALENDAR'); - $calendar->version = '2.0'; - $calendar->prodid = '-//Sabre//Sabre VObject ' . Version::VERSION . '//EN'; - $calendar->calscale = 'GREGORIAN'; - } - - $vfreebusy = Component::create('VFREEBUSY'); - $calendar->add($vfreebusy); - - if ($this->start) { - $dtstart = Property::create('DTSTART'); - $dtstart->setDateTime($this->start,Property\DateTime::UTC); - $vfreebusy->add($dtstart); - } - if ($this->end) { - $dtend = Property::create('DTEND'); - $dtend->setDateTime($this->end,Property\DateTime::UTC); - $vfreebusy->add($dtend); - } - $dtstamp = Property::create('DTSTAMP'); - $dtstamp->setDateTime(new \DateTime('now'), Property\DateTime::UTC); - $vfreebusy->add($dtstamp); - - foreach($busyTimes as $busyTime) { - - $busyTime[0]->setTimeZone(new \DateTimeZone('UTC')); - $busyTime[1]->setTimeZone(new \DateTimeZone('UTC')); - - $prop = Property::create( - 'FREEBUSY', - $busyTime[0]->format('Ymd\\THis\\Z') . '/' . $busyTime[1]->format('Ymd\\THis\\Z') - ); - $prop['FBTYPE'] = $busyTime[2]; - $vfreebusy->add($prop); - - } - - return $calendar; - - } - -} -
--- a/plugins/libcalendaring/lib/Sabre/VObject/Node.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,187 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Base class for all nodes - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -abstract class Node implements \IteratorAggregate, \ArrayAccess, \Countable { - - /** - * The following constants are used by the validate() method. - */ - const REPAIR = 1; - - /** - * Turns the object back into a serialized blob. - * - * @return string - */ - abstract function serialize(); - - /** - * Iterator override - * - * @var ElementList - */ - protected $iterator = null; - - /** - * A link to the parent node - * - * @var Node - */ - public $parent = null; - - /** - * Validates the node for correctness. - * - * The following options are supported: - * - Node::REPAIR - If something is broken, and automatic repair may - * be attempted. - * - * An array is returned with warnings. - * - * Every item in the array has the following properties: - * * level - (number between 1 and 3 with severity information) - * * message - (human readable message) - * * node - (reference to the offending node) - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - return array(); - - } - - /* {{{ IteratorAggregator interface */ - - /** - * Returns the iterator for this object - * - * @return ElementList - */ - public function getIterator() { - - if (!is_null($this->iterator)) - return $this->iterator; - - return new ElementList(array($this)); - - } - - /** - * Sets the overridden iterator - * - * Note that this is not actually part of the iterator interface - * - * @param ElementList $iterator - * @return void - */ - public function setIterator(ElementList $iterator) { - - $this->iterator = $iterator; - - } - - /* }}} */ - - /* {{{ Countable interface */ - - /** - * Returns the number of elements - * - * @return int - */ - public function count() { - - $it = $this->getIterator(); - return $it->count(); - - } - - /* }}} */ - - /* {{{ ArrayAccess Interface */ - - - /** - * Checks if an item exists through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @return bool - */ - public function offsetExists($offset) { - - $iterator = $this->getIterator(); - return $iterator->offsetExists($offset); - - } - - /** - * Gets an item through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @return mixed - */ - public function offsetGet($offset) { - - $iterator = $this->getIterator(); - return $iterator->offsetGet($offset); - - } - - /** - * Sets an item through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @param mixed $value - * @return void - */ - public function offsetSet($offset,$value) { - - $iterator = $this->getIterator(); - $iterator->offsetSet($offset,$value); - - // @codeCoverageIgnoreStart - // - // This method always throws an exception, so we ignore the closing - // brace - } - // @codeCoverageIgnoreEnd - - /** - * Sets an item through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @return void - */ - public function offsetUnset($offset) { - - $iterator = $this->getIterator(); - $iterator->offsetUnset($offset); - - // @codeCoverageIgnoreStart - // - // This method always throws an exception, so we ignore the closing - // brace - } - // @codeCoverageIgnoreEnd - - /* }}} */ - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Parameter.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,102 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * VObject Parameter - * - * This class represents a parameter. A parameter is always tied to a property. - * In the case of: - * DTSTART;VALUE=DATE:20101108 - * VALUE=DATE would be the parameter name and value. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class Parameter extends Node { - - /** - * Parameter name - * - * @var string - */ - public $name; - - /** - * Parameter value - * - * @var string - */ - public $value; - - /** - * Sets up the object - * - * @param string $name - * @param string $value - */ - public function __construct($name, $value = null) { - - if (!is_scalar($value) && !is_null($value)) { - throw new \InvalidArgumentException('The value argument must be a scalar value or null'); - } - - $this->name = strtoupper($name); - $this->value = $value; - - } - - /** - * Returns the parameter's internal value. - * - * @return string - */ - public function getValue() { - - return $this->value; - - } - - - /** - * Turns the object back into a serialized blob. - * - * @return string - */ - public function serialize() { - - if (is_null($this->value)) { - return $this->name; - } - $src = array( - '\\', - "\n", - ); - $out = array( - '\\\\', - '\n', - ); - - // quote parameters according to RFC 5545, Section 3.2 - $quotes = ''; - if (preg_match('/[:;,]/', $this->value)) { - $quotes = '"'; - } - - return $this->name . '=' . $quotes . str_replace($src, $out, $this->value) . $quotes; - - } - - /** - * Called when this object is being cast to a string - * - * @return string - */ - public function __toString() { - - return $this->value; - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/ParseException.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,12 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Exception thrown by Reader if an invalid object was attempted to be parsed. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class ParseException extends \Exception { }
--- a/plugins/libcalendaring/lib/Sabre/VObject/Property.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,453 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * VObject Property - * - * A property in VObject is usually in the form PARAMNAME:paramValue. - * An example is : SUMMARY:Weekly meeting - * - * Properties can also have parameters: - * SUMMARY;LANG=en:Weekly meeting. - * - * Parameters can be accessed using the ArrayAccess interface. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class Property extends Node { - - /** - * Propertyname - * - * @var string - */ - public $name; - - /** - * Group name - * - * This may be something like 'HOME' for vcards. - * - * @var string - */ - public $group; - - /** - * Property parameters - * - * @var array - */ - public $parameters = array(); - - /** - * Property value - * - * @var string - */ - public $value; - - /** - * If properties are added to this map, they will be automatically mapped - * to their respective classes, if parsed by the reader or constructed with - * the 'create' method. - * - * @var array - */ - static public $classMap = array( - 'COMPLETED' => 'Sabre\\VObject\\Property\\DateTime', - 'CREATED' => 'Sabre\\VObject\\Property\\DateTime', - 'DTEND' => 'Sabre\\VObject\\Property\\DateTime', - 'DTSTAMP' => 'Sabre\\VObject\\Property\\DateTime', - 'DTSTART' => 'Sabre\\VObject\\Property\\DateTime', - 'DUE' => 'Sabre\\VObject\\Property\\DateTime', - 'EXDATE' => 'Sabre\\VObject\\Property\\MultiDateTime', - 'LAST-MODIFIED' => 'Sabre\\VObject\\Property\\DateTime', - 'RECURRENCE-ID' => 'Sabre\\VObject\\Property\\DateTime', - 'TRIGGER' => 'Sabre\\VObject\\Property\\DateTime', - 'N' => 'Sabre\\VObject\\Property\\Compound', - 'ORG' => 'Sabre\\VObject\\Property\\Compound', - 'ADR' => 'Sabre\\VObject\\Property\\Compound', - 'CATEGORIES' => 'Sabre\\VObject\\Property\\Compound', - ); - - /** - * Creates the new property by name, but in addition will also see if - * there's a class mapped to the property name. - * - * Parameters can be specified with the optional third argument. Parameters - * must be a key->value map of the parameter name, and value. If the value - * is specified as an array, it is assumed that multiple parameters with - * the same name should be added. - * - * @param string $name - * @param string $value - * @param array $parameters - * @return Property - */ - static public function create($name, $value = null, array $parameters = array()) { - - $name = strtoupper($name); - $shortName = $name; - $group = null; - if (strpos($shortName,'.')!==false) { - list($group, $shortName) = explode('.', $shortName); - } - - if (isset(self::$classMap[$shortName])) { - return new self::$classMap[$shortName]($name, $value, $parameters); - } else { - return new self($name, $value, $parameters); - } - - } - - /** - * Creates a new property object - * - * Parameters can be specified with the optional third argument. Parameters - * must be a key->value map of the parameter name, and value. If the value - * is specified as an array, it is assumed that multiple parameters with - * the same name should be added. - * - * @param string $name - * @param string $value - * @param array $parameters - */ - public function __construct($name, $value = null, array $parameters = array()) { - - if (!is_scalar($value) && !is_null($value)) { - throw new \InvalidArgumentException('The value argument must be scalar or null'); - } - - $name = strtoupper($name); - $group = null; - if (strpos($name,'.')!==false) { - list($group, $name) = explode('.', $name); - } - $this->name = $name; - $this->group = $group; - $this->setValue($value); - - foreach($parameters as $paramName => $paramValues) { - - if (!is_array($paramValues)) { - $paramValues = array($paramValues); - } - - foreach($paramValues as $paramValue) { - $this->add($paramName, $paramValue); - } - - } - - } - - /** - * Updates the internal value - * - * @param string $value - * @return void - */ - public function setValue($value) { - - $this->value = $value; - - } - - /** - * Returns the internal value - * - * @param string $value - * @return string - */ - public function getValue() { - - return $this->value; - - } - - /** - * Turns the object back into a serialized blob. - * - * @return string - */ - public function serialize() { - - $str = $this->name; - if ($this->group) $str = $this->group . '.' . $this->name; - - foreach($this->parameters as $param) { - - $str.=';' . $param->serialize(); - - } - - $src = array( - '\\', - "\n", - "\r", - ); - $out = array( - '\\\\', - '\n', - '', - ); - - // avoid double-escaping of \, and \; from Compound properties - if (method_exists($this, 'setParts')) { - $src[] = '\\\\,'; - $out[] = '\\,'; - $src[] = '\\\\;'; - $out[] = '\\;'; - } - - $str.=':' . str_replace($src, $out, $this->value); - - $out = ''; - while(strlen($str)>0) { - if (strlen($str)>75) { - $out.= mb_strcut($str,0,75,'utf-8') . "\r\n"; - $str = ' ' . mb_strcut($str,75,strlen($str),'utf-8'); - } else { - $out.=$str . "\r\n"; - $str=''; - break; - } - } - - return $out; - - } - - /** - * Adds a new componenten or element - * - * You can call this method with the following syntaxes: - * - * add(Parameter $element) - * add(string $name, $value) - * - * The first version adds an Parameter - * The second adds a property as a string. - * - * @param mixed $item - * @param mixed $itemValue - * @return void - */ - public function add($item, $itemValue = null) { - - if ($item instanceof Parameter) { - if (!is_null($itemValue)) { - throw new \InvalidArgumentException('The second argument must not be specified, when passing a VObject'); - } - $item->parent = $this; - $this->parameters[] = $item; - } elseif(is_string($item)) { - - $parameter = new Parameter($item,$itemValue); - $parameter->parent = $this; - $this->parameters[] = $parameter; - - } else { - - throw new \InvalidArgumentException('The first argument must either be a Node a string'); - - } - - } - - /* ArrayAccess interface {{{ */ - - /** - * Checks if an array element exists - * - * @param mixed $name - * @return bool - */ - public function offsetExists($name) { - - if (is_int($name)) return parent::offsetExists($name); - - $name = strtoupper($name); - - foreach($this->parameters as $parameter) { - if ($parameter->name == $name) return true; - } - return false; - - } - - /** - * Returns a parameter, or parameter list. - * - * @param string $name - * @return Node - */ - public function offsetGet($name) { - - if (is_int($name)) return parent::offsetGet($name); - $name = strtoupper($name); - - $result = array(); - foreach($this->parameters as $parameter) { - if ($parameter->name == $name) - $result[] = $parameter; - } - - if (count($result)===0) { - return null; - } elseif (count($result)===1) { - return $result[0]; - } else { - $result[0]->setIterator(new ElementList($result)); - return $result[0]; - } - - } - - /** - * Creates a new parameter - * - * @param string $name - * @param mixed $value - * @return void - */ - public function offsetSet($name, $value) { - - if (is_int($name)) parent::offsetSet($name, $value); - - if (is_scalar($value)) { - if (!is_string($name)) - throw new \InvalidArgumentException('A parameter name must be specified. This means you cannot use the $array[]="string" to add parameters.'); - - $this->offsetUnset($name); - $parameter = new Parameter($name, $value); - $parameter->parent = $this; - $this->parameters[] = $parameter; - - } elseif ($value instanceof Parameter) { - if (!is_null($name)) - throw new \InvalidArgumentException('Don\'t specify a parameter name if you\'re passing a \\Sabre\\VObject\\Parameter. Add using $array[]=$parameterObject.'); - - $value->parent = $this; - $this->parameters[] = $value; - } else { - throw new \InvalidArgumentException('You can only add parameters to the property object'); - } - - } - - /** - * Removes one or more parameters with the specified name - * - * @param string $name - * @return void - */ - public function offsetUnset($name) { - - if (is_int($name)) parent::offsetUnset($name); - $name = strtoupper($name); - - foreach($this->parameters as $key=>$parameter) { - if ($parameter->name == $name) { - $parameter->parent = null; - unset($this->parameters[$key]); - } - - } - - } - - /* }}} */ - - /** - * Called when this object is being cast to a string - * - * @return string - */ - public function __toString() { - - return (string)$this->value; - - } - - /** - * This method is automatically called when the object is cloned. - * Specifically, this will ensure all child elements are also cloned. - * - * @return void - */ - public function __clone() { - - foreach($this->parameters as $key=>$child) { - $this->parameters[$key] = clone $child; - $this->parameters[$key]->parent = $this; - } - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * - Node::REPAIR - If something is broken, and automatic repair may - * be attempted. - * - * An array is returned with warnings. - * - * Every item in the array has the following properties: - * * level - (number between 1 and 3 with severity information) - * * message - (human readable message) - * * node - (reference to the offending node) - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - $warnings = array(); - - // Checking if our value is UTF-8 - if (!StringUtil::isUTF8($this->value)) { - $warnings[] = array( - 'level' => 1, - 'message' => 'Property is not valid UTF-8!', - 'node' => $this, - ); - if ($options & self::REPAIR) { - $this->value = StringUtil::convertToUTF8($this->value); - } - } - - // Checking if the propertyname does not contain any invalid bytes. - if (!preg_match('/^([A-Z0-9-]+)$/', $this->name)) { - $warnings[] = array( - 'level' => 1, - 'message' => 'The propertyname: ' . $this->name . ' contains invalid characters. Only A-Z, 0-9 and - are allowed', - 'node' => $this, - ); - if ($options & self::REPAIR) { - // Uppercasing and converting underscores to dashes. - $this->name = strtoupper( - str_replace('_', '-', $this->name) - ); - // Removing every other invalid character - $this->name = preg_replace('/([^A-Z0-9-])/u', '', $this->name); - - } - - } - - // Validating inner parameters - foreach($this->parameters as $param) { - $warnings = array_merge($warnings, $param->validate($options)); - } - - return $warnings; - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Property/Compound.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,125 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject; - -/** - * Compound property. - * - * This class adds (de)serialization of compound properties to/from arrays. - * - * Currently the following properties from RFC 6350 are mapped to use this - * class: - * - * N: Section 6.2.2 - * ADR: Section 6.3.1 - * ORG: Section 6.6.4 - * CATEGORIES: Section 6.7.1 - * - * In order to use this correctly, you must call setParts and getParts to - * retrieve and modify dates respectively. - * - * @author Thomas Tanghus (http://tanghus.net/) - * @author Lars Kneschke - * @author Evert Pot (http://evertpot.com/) - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class Compound extends VObject\Property { - - /** - * If property names are added to this map, they will be (de)serialised as arrays - * using the getParts() and setParts() methods. - * The keys are the property names, values are delimiter chars. - * - * @var array - */ - static public $delimiterMap = array( - 'N' => ';', - 'ADR' => ';', - 'ORG' => ';', - 'CATEGORIES' => ',', - ); - - /** - * The currently used delimiter. - * - * @var string - */ - protected $delimiter = null; - - /** - * Get a compound value as an array. - * - * @param $name string - * @return array - */ - public function getParts() { - - if (is_null($this->value)) { - return array(); - } - - $delimiter = $this->getDelimiter(); - - // split by any $delimiter which is NOT prefixed by a slash. - // Note that this is not a a perfect solution. If a value is prefixed - // by two slashes, it should actually be split anyway. - // - // Hopefully we can fix this better in a future version, where we can - // break compatibility a bit. - $compoundValues = preg_split("/(?<!\\\)$delimiter/", $this->value); - - // remove slashes from any semicolon and comma left escaped in the single values - $compoundValues = array_map( - function($val) { - return strtr($val, array('\,' => ',', '\;' => ';')); - }, $compoundValues); - - return $compoundValues; - - } - - /** - * Returns the delimiter for this property. - * - * @return string - */ - public function getDelimiter() { - - if (!$this->delimiter) { - if (isset(self::$delimiterMap[$this->name])) { - $this->delimiter = self::$delimiterMap[$this->name]; - } else { - // To be a bit future proof, we are going to default the - // delimiter to ; - $this->delimiter = ';'; - } - } - return $this->delimiter; - - } - - /** - * Set a compound value as an array. - * - * - * @param $name string - * @return array - */ - public function setParts(array $values) { - - // add slashes to all semicolons and commas in the single values - $values = array_map( - function($val) { - return strtr($val, array(',' => '\,', ';' => '\;')); - }, $values); - - $this->setValue( - implode($this->getDelimiter(), $values) - ); - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Property/DateTime.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,245 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject; - -/** - * DateTime property - * - * This element is used for iCalendar properties such as the DTSTART property. - * It basically provides a few helper functions that make it easier to deal - * with these. It supports both DATE-TIME and DATE values. - * - * In order to use this correctly, you must call setDateTime and getDateTime to - * retrieve and modify dates respectively. - * - * If you use the 'value' or properties directly, this object does not keep - * reference and results might appear incorrectly. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class DateTime extends VObject\Property { - - /** - * Local 'floating' time - */ - const LOCAL = 1; - - /** - * UTC-based time - */ - const UTC = 2; - - /** - * Local time plus timezone - */ - const LOCALTZ = 3; - - /** - * Only a date, time is ignored - */ - const DATE = 4; - - /** - * DateTime representation - * - * @var \DateTime - */ - protected $dateTime; - - /** - * dateType - * - * @var int - */ - protected $dateType; - - /** - * Updates the Date and Time. - * - * @param \DateTime $dt - * @param int $dateType - * @return void - */ - public function setDateTime(\DateTime $dt, $dateType = self::LOCALTZ) { - - switch($dateType) { - - case self::LOCAL : - $this->setValue($dt->format('Ymd\\THis')); - $this->offsetUnset('VALUE'); - $this->offsetUnset('TZID'); - $this->offsetSet('VALUE','DATE-TIME'); - break; - case self::UTC : - $dt->setTimeZone(new \DateTimeZone('UTC')); - $this->setValue($dt->format('Ymd\\THis\\Z')); - $this->offsetUnset('VALUE'); - $this->offsetUnset('TZID'); - $this->offsetSet('VALUE','DATE-TIME'); - break; - case self::LOCALTZ : - $this->setValue($dt->format('Ymd\\THis')); - $this->offsetUnset('VALUE'); - $this->offsetUnset('TZID'); - $this->offsetSet('VALUE','DATE-TIME'); - $this->offsetSet('TZID', $dt->getTimeZone()->getName()); - break; - case self::DATE : - $this->setValue($dt->format('Ymd')); - $this->offsetUnset('VALUE'); - $this->offsetUnset('TZID'); - $this->offsetSet('VALUE','DATE'); - break; - default : - throw new \InvalidArgumentException('You must pass a valid dateType constant'); - - } - $this->dateTime = $dt; - $this->dateType = $dateType; - - } - - /** - * Returns the current DateTime value. - * - * If no value was set, this method returns null. - * - * @return \DateTime|null - */ - public function getDateTime() { - - if ($this->dateTime) - return $this->dateTime; - - list( - $this->dateType, - $this->dateTime - ) = self::parseData($this->value, $this); - return $this->dateTime; - - } - - /** - * Returns the type of Date format. - * - * This method returns one of the format constants. If no date was set, - * this method will return null. - * - * @return int|null - */ - public function getDateType() { - - if ($this->dateType) - return $this->dateType; - - list( - $this->dateType, - $this->dateTime, - ) = self::parseData($this->value, $this); - return $this->dateType; - - } - - /** - * This method will return true, if the property had a date and a time, as - * opposed to only a date. - * - * @return bool - */ - public function hasTime() { - - return $this->getDateType()!==self::DATE; - - } - - /** - * Parses the internal data structure to figure out what the current date - * and time is. - * - * The returned array contains two elements: - * 1. A 'DateType' constant (as defined on this class), or null. - * 2. A DateTime object (or null) - * - * @param string|null $propertyValue The string to parse (yymmdd or - * ymmddThhmmss, etc..) - * @param \Sabre\VObject\Property|null $property The instance of the - * property we're parsing. - * @return array - */ - static public function parseData($propertyValue, VObject\Property $property = null) { - - if (is_null($propertyValue)) { - return array(null, null); - } - - $date = '(?P<year>[1-2][0-9]{3})(?P<month>[0-1][0-9])(?P<date>[0-3][0-9])'; - $time = '(?P<hour>[0-2][0-9])(?P<minute>[0-5][0-9])(?P<second>[0-5][0-9])'; - $regex = "/^$date(T$time(?P<isutc>Z)?)?$/"; - - if (!preg_match($regex, $propertyValue, $matches)) { - throw new \InvalidArgumentException($propertyValue . ' is not a valid \DateTime or Date string'); - } - - if (!isset($matches['hour'])) { - // Date-only - return array( - self::DATE, - new \DateTime($matches['year'] . '-' . $matches['month'] . '-' . $matches['date'] . ' 00:00:00', new \DateTimeZone('UTC')), - ); - } - - $dateStr = - $matches['year'] .'-' . - $matches['month'] . '-' . - $matches['date'] . ' ' . - $matches['hour'] . ':' . - $matches['minute'] . ':' . - $matches['second']; - - if (isset($matches['isutc'])) { - $dt = new \DateTime($dateStr,new \DateTimeZone('UTC')); - $dt->setTimeZone(new \DateTimeZone('UTC')); - return array( - self::UTC, - $dt - ); - } - - // Finding the timezone. - $tzid = $property['TZID']; - if (!$tzid) { - // This was a floating time string. This implies we use the - // timezone from date_default_timezone_set / date.timezone ini - // setting. - return array( - self::LOCAL, - new \DateTime($dateStr) - ); - } - - // To look up the timezone, we must first find the VCALENDAR component. - $root = $property; - while($root->parent) { - $root = $root->parent; - } - if ($root->name === 'VCALENDAR') { - $tz = VObject\TimeZoneUtil::getTimeZone((string)$tzid, $root); - } else { - $tz = VObject\TimeZoneUtil::getTimeZone((string)$tzid); - } - - $dt = new \DateTime($dateStr, $tz); - $dt->setTimeZone($tz); - - return array( - self::LOCALTZ, - $dt - ); - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Property/MultiDateTime.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,180 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject; - -/** - * Multi-DateTime property - * - * This element is used for iCalendar properties such as the EXDATE property. - * It basically provides a few helper functions that make it easier to deal - * with these. It supports both DATE-TIME and DATE values. - * - * In order to use this correctly, you must call setDateTimes and getDateTimes - * to retrieve and modify dates respectively. - * - * If you use the 'value' or properties directly, this object does not keep - * reference and results might appear incorrectly. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class MultiDateTime extends VObject\Property { - - /** - * DateTime representation - * - * @var DateTime[] - */ - protected $dateTimes; - - /** - * dateType - * - * This is one of the Sabre\VObject\Property\DateTime constants. - * - * @var int - */ - protected $dateType; - - /** - * Updates the value - * - * @param array $dt Must be an array of DateTime objects. - * @param int $dateType - * @return void - */ - public function setDateTimes(array $dt, $dateType = VObject\Property\DateTime::LOCALTZ) { - - foreach($dt as $i) - if (!$i instanceof \DateTime) - throw new \InvalidArgumentException('You must pass an array of DateTime objects'); - - $this->offsetUnset('VALUE'); - $this->offsetUnset('TZID'); - switch($dateType) { - - case DateTime::LOCAL : - $val = array(); - foreach($dt as $i) { - $val[] = $i->format('Ymd\\THis'); - } - $this->setValue(implode(',',$val)); - $this->offsetSet('VALUE','DATE-TIME'); - break; - case DateTime::UTC : - $val = array(); - foreach($dt as $i) { - $i->setTimeZone(new \DateTimeZone('UTC')); - $val[] = $i->format('Ymd\\THis\\Z'); - } - $this->setValue(implode(',',$val)); - $this->offsetSet('VALUE','DATE-TIME'); - break; - case DateTime::LOCALTZ : - $val = array(); - foreach($dt as $i) { - $val[] = $i->format('Ymd\\THis'); - } - $this->setValue(implode(',',$val)); - $this->offsetSet('VALUE','DATE-TIME'); - $this->offsetSet('TZID', $dt[0]->getTimeZone()->getName()); - break; - case DateTime::DATE : - $val = array(); - foreach($dt as $i) { - $val[] = $i->format('Ymd'); - } - $this->setValue(implode(',',$val)); - $this->offsetSet('VALUE','DATE'); - break; - default : - throw new \InvalidArgumentException('You must pass a valid dateType constant'); - - } - $this->dateTimes = $dt; - $this->dateType = $dateType; - - } - - /** - * Returns the current DateTime value. - * - * If no value was set, this method returns null. - * - * @return array|null - */ - public function getDateTimes() { - - if ($this->dateTimes) - return $this->dateTimes; - - $dts = array(); - - if (!$this->value) { - $this->dateTimes = null; - $this->dateType = null; - return null; - } - - foreach(explode(',',$this->value) as $val) { - list( - $type, - $dt - ) = DateTime::parseData($val, $this); - $dts[] = $dt; - $this->dateType = $type; - } - $this->dateTimes = $dts; - return $this->dateTimes; - - } - - /** - * Returns the type of Date format. - * - * This method returns one of the format constants. If no date was set, - * this method will return null. - * - * @return int|null - */ - public function getDateType() { - - if ($this->dateType) - return $this->dateType; - - if (!$this->value) { - $this->dateTimes = null; - $this->dateType = null; - return null; - } - - $dts = array(); - foreach(explode(',',$this->value) as $val) { - list( - $type, - $dt - ) = DateTime::parseData($val, $this); - $dts[] = $dt; - $this->dateType = $type; - } - $this->dateTimes = $dts; - return $this->dateType; - - } - - /** - * This method will return true, if the property had a date and a time, as - * opposed to only a date. - * - * @return bool - */ - public function hasTime() { - - return $this->getDateType()!==DateTime::DATE; - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Reader.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,223 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * VCALENDAR/VCARD reader - * - * This class reads the vobject file, and returns a full element tree. - * - * TODO: this class currently completely works 'statically'. This is pointless, - * and defeats OOP principals. Needs refactoring in a future version. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class Reader { - - /** - * If this option is passed to the reader, it will be less strict about the - * validity of the lines. - * - * Currently using this option just means, that it will accept underscores - * in property names. - */ - const OPTION_FORGIVING = 1; - - /** - * If this option is turned on, any lines we cannot parse will be ignored - * by the reader. - */ - const OPTION_IGNORE_INVALID_LINES = 2; - - /** - * Parses the file and returns the top component - * - * The options argument is a bitfield. Pass any of the OPTIONS constant to - * alter the parsers' behaviour. - * - * @param string $data - * @param int $options - * @return Node - */ - static function read($data, $options = 0) { - - // Normalizing newlines - $data = str_replace(array("\r","\n\n"), array("\n","\n"), $data); - - $lines = explode("\n", $data); - - // Unfolding lines - $lines2 = array(); - foreach($lines as $line) { - - // Skipping empty lines - if (!$line) continue; - - if ($line[0]===" " || $line[0]==="\t") { - $lines2[count($lines2)-1].=substr($line,1); - } else { - $lines2[] = $line; - } - - } - - unset($lines); - - reset($lines2); - - return self::readLine($lines2, $options); - - } - - /** - * Reads and parses a single line. - * - * This method receives the full array of lines. The array pointer is used - * to traverse. - * - * This method returns null if an invalid line was encountered, and the - * IGNORE_INVALID_LINES option was turned on. - * - * @param array $lines - * @param int $options See the OPTIONS constants. - * @return Node - */ - static private function readLine(&$lines, $options = 0) { - - $line = current($lines); - $lineNr = key($lines); - next($lines); - - // Components - if (strtoupper(substr($line,0,6)) === "BEGIN:") { - - $componentName = strtoupper(substr($line,6)); - $obj = Component::create($componentName); - - $nextLine = current($lines); - - while(strtoupper(substr($nextLine,0,4))!=="END:") { - - $parsedLine = self::readLine($lines, $options); - $nextLine = current($lines); - - if (is_null($parsedLine)) { - continue; - } - $obj->add($parsedLine); - - if ($nextLine===false) - throw new ParseException('Invalid VObject. Document ended prematurely.'); - - } - - // Checking component name of the 'END:' line. - if (substr($nextLine,4)!==$obj->name) { - throw new ParseException('Invalid VObject, expected: "END:' . $obj->name . '" got: "' . $nextLine . '"'); - } - next($lines); - - return $obj; - - } - - // Properties - //$result = preg_match('/(?P<name>[A-Z0-9-]+)(?:;(?P<parameters>^(?<!:):))(.*)$/',$line,$matches); - - if ($options & self::OPTION_FORGIVING) { - $token = '[A-Z0-9-\._]+'; - } else { - $token = '[A-Z0-9-\.]+'; - } - $parameters = "(?:;(?P<parameters>([^:^\"]|\"([^\"]*)\")*))?"; - $regex = "/^(?P<name>$token)$parameters:(?P<value>.*)$/i"; - - $result = preg_match($regex,$line,$matches); - - if (!$result) { - if ($options & self::OPTION_IGNORE_INVALID_LINES) { - return null; - } else { - throw new ParseException('Invalid VObject, line ' . ($lineNr+1) . ' did not follow the icalendar/vcard format'); - } - } - - $propertyName = strtoupper($matches['name']); - $propertyValue = preg_replace_callback('#(\\\\(\\\\|N|n))#',function($matches) { - if ($matches[2]==='n' || $matches[2]==='N') { - return "\n"; - } else { - return $matches[2]; - } - }, $matches['value']); - - $obj = Property::create($propertyName, $propertyValue); - - if ($matches['parameters']) { - - foreach(self::readParameters($matches['parameters']) as $param) { - $obj->add($param); - } - - } - - return $obj; - - - } - - /** - * Reads a parameter list from a property - * - * This method returns an array of Parameter - * - * @param string $parameters - * @return array - */ - static private function readParameters($parameters) { - - $token = '[A-Z0-9-]+'; - - $paramValue = '(?P<paramValue>[^\"^;]*|"[^"]*")'; - - $regex = "/(?<=^|;)(?P<paramName>$token)(=$paramValue(?=$|;))?/i"; - preg_match_all($regex, $parameters, $matches, PREG_SET_ORDER); - - $params = array(); - foreach($matches as $match) { - - if (!isset($match['paramValue'])) { - - $value = null; - - } else { - - $value = $match['paramValue']; - - if (isset($value[0]) && $value[0]==='"') { - // Stripping quotes, if needed - $value = substr($value,1,strlen($value)-2); - } - - $value = preg_replace_callback('#(\\\\(\\\\|N|n|;|,))#',function($matches) { - if ($matches[2]==='n' || $matches[2]==='N') { - return "\n"; - } else { - return $matches[2]; - } - }, $value); - - } - - $params[] = new Parameter($match['paramName'], $value); - - } - - return $params; - - } - - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/RecurrenceIterator.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1144 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * This class is used to determine new for a recurring event, when the next - * events occur. - * - * This iterator may loop infinitely in the future, therefore it is important - * that if you use this class, you set hard limits for the amount of iterations - * you want to handle. - * - * Note that currently there is not full support for the entire iCalendar - * specification, as it's very complex and contains a lot of permutations - * that's not yet used very often in software. - * - * For the focus has been on features as they actually appear in Calendaring - * software, but this may well get expanded as needed / on demand - * - * The following RRULE properties are supported - * * UNTIL - * * INTERVAL - * * COUNT - * * FREQ=DAILY - * * BYDAY - * * BYHOUR - * * FREQ=WEEKLY - * * BYDAY - * * BYHOUR - * * WKST - * * FREQ=MONTHLY - * * BYMONTHDAY - * * BYDAY - * * BYSETPOS - * * FREQ=YEARLY - * * BYMONTH - * * BYMONTHDAY (only if BYMONTH is also set) - * * BYDAY (only if BYMONTH is also set) - * - * Anything beyond this is 'undefined', which means that it may get ignored, or - * you may get unexpected results. The effect is that in some applications the - * specified recurrence may look incorrect, or is missing. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class RecurrenceIterator implements \Iterator { - - /** - * The initial event date - * - * @var DateTime - */ - public $startDate; - - /** - * The end-date of the initial event - * - * @var DateTime - */ - public $endDate; - - /** - * The 'current' recurrence. - * - * This will be increased for every iteration. - * - * @var DateTime - */ - public $currentDate; - - - /** - * List of dates that are excluded from the rules. - * - * This list contains the items that have been overriden by the EXDATE - * property. - * - * @var array - */ - public $exceptionDates = array(); - - /** - * Base event - * - * @var Component\VEvent - */ - public $baseEvent; - - /** - * List of dates that are overridden by other events. - * Similar to $overriddenEvents, but this just contains the original dates. - * - * @var array - */ - public $overriddenDates = array(); - - /** - * list of events that are 'overridden'. - * - * This is an array of Component\VEvent objects. - * - * @var array - */ - public $overriddenEvents = array(); - - /** - * Frequency is one of: secondly, minutely, hourly, daily, weekly, monthly, - * yearly. - * - * @var string - */ - public $frequency; - - /** - * The last instance of this recurrence, inclusively - * - * @var DateTime|null - */ - public $until; - - /** - * The number of recurrences, or 'null' if infinitely recurring. - * - * @var int - */ - public $count; - - /** - * The interval. - * - * If for example frequency is set to daily, interval = 2 would mean every - * 2 days. - * - * @var int - */ - public $interval = 1; - - /** - * Which seconds to recur. - * - * This is an array of integers (between 0 and 60) - * - * @var array - */ - public $bySecond; - - /** - * Which minutes to recur - * - * This is an array of integers (between 0 and 59) - * - * @var array - */ - public $byMinute; - - /** - * Which hours to recur - * - * This is an array of integers (between 0 and 23) - * - * @var array - */ - public $byHour; - - /** - * Which weekdays to recur. - * - * This is an array of weekdays - * - * This may also be preceeded by a positive or negative integer. If present, - * this indicates the nth occurrence of a specific day within the monthly or - * yearly rrule. For instance, -2TU indicates the second-last tuesday of - * the month, or year. - * - * @var array - */ - public $byDay; - - /** - * Which days of the month to recur - * - * This is an array of days of the months (1-31). The value can also be - * negative. -5 for instance means the 5th last day of the month. - * - * @var array - */ - public $byMonthDay; - - /** - * Which days of the year to recur. - * - * This is an array with days of the year (1 to 366). The values can also - * be negative. For instance, -1 will always represent the last day of the - * year. (December 31st). - * - * @var array - */ - public $byYearDay; - - /** - * Which week numbers to recur. - * - * This is an array of integers from 1 to 53. The values can also be - * negative. -1 will always refer to the last week of the year. - * - * @var array - */ - public $byWeekNo; - - /** - * Which months to recur - * - * This is an array of integers from 1 to 12. - * - * @var array - */ - public $byMonth; - - /** - * Which items in an existing st to recur. - * - * These numbers work together with an existing by* rule. It specifies - * exactly which items of the existing by-rule to filter. - * - * Valid values are 1 to 366 and -1 to -366. As an example, this can be - * used to recur the last workday of the month. - * - * This would be done by setting frequency to 'monthly', byDay to - * 'MO,TU,WE,TH,FR' and bySetPos to -1. - * - * @var array - */ - public $bySetPos; - - /** - * When a week starts - * - * @var string - */ - public $weekStart = 'MO'; - - /** - * The current item in the list - * - * @var int - */ - public $counter = 0; - - /** - * Simple mapping from iCalendar day names to day numbers - * - * @var array - */ - private $dayMap = array( - 'SU' => 0, - 'MO' => 1, - 'TU' => 2, - 'WE' => 3, - 'TH' => 4, - 'FR' => 5, - 'SA' => 6, - ); - - /** - * Mappings between the day number and english day name. - * - * @var array - */ - private $dayNames = array( - 0 => 'Sunday', - 1 => 'Monday', - 2 => 'Tuesday', - 3 => 'Wednesday', - 4 => 'Thursday', - 5 => 'Friday', - 6 => 'Saturday', - ); - - /** - * If the current iteration of the event is an overriden event, this - * property will hold the VObject - * - * @var Component - */ - private $currentOverriddenEvent; - - /** - * This property may contain the date of the next not-overridden event. - * This date is calculated sometimes a bit early, before overridden events - * are evaluated. - * - * @var DateTime - */ - private $nextDate; - - /** - * This counts the number of overridden events we've handled so far - * - * @var int - */ - private $handledOverridden = 0; - - /** - * Creates the iterator - * - * You should pass a VCALENDAR component, as well as the UID of the event - * we're going to traverse. - * - * @param Component $vcal - * @param string|null $uid - */ - public function __construct(Component $vcal, $uid=null) { - - if (is_null($uid)) { - if ($vcal->name === 'VCALENDAR') { - throw new \InvalidArgumentException('If you pass a VCALENDAR object, you must pass a uid argument as well'); - } - $components = array($vcal); - $uid = (string)$vcal->uid; - } else { - $components = $vcal->select('VEVENT'); - } - foreach($components as $component) { - if ((string)$component->uid == $uid) { - if (isset($component->{'RECURRENCE-ID'})) { - $this->overriddenEvents[$component->DTSTART->getDateTime()->getTimeStamp()] = $component; - $this->overriddenDates[] = $component->{'RECURRENCE-ID'}->getDateTime(); - } else { - $this->baseEvent = $component; - } - } - } - - ksort($this->overriddenEvents); - - if (!$this->baseEvent) { - throw new \InvalidArgumentException('Could not find a base event with uid: ' . $uid); - } - - $this->startDate = clone $this->baseEvent->DTSTART->getDateTime(); - - $this->endDate = null; - if (isset($this->baseEvent->DTEND)) { - $this->endDate = clone $this->baseEvent->DTEND->getDateTime(); - } else { - $this->endDate = clone $this->startDate; - if (isset($this->baseEvent->DURATION)) { - $this->endDate->add(DateTimeParser::parse($this->baseEvent->DURATION->value)); - } elseif ($this->baseEvent->DTSTART->getDateType()===Property\DateTime::DATE) { - $this->endDate->modify('+1 day'); - } - } - $this->currentDate = clone $this->startDate; - - $rrule = (string)$this->baseEvent->RRULE; - - $parts = explode(';', $rrule); - - // If no rrule was specified, we create a default setting - if (!$rrule) { - $this->frequency = 'daily'; - $this->count = 1; - } else foreach($parts as $part) { - - list($key, $value) = explode('=', $part, 2); - - switch(strtoupper($key)) { - - case 'FREQ' : - if (!in_array( - strtolower($value), - array('secondly','minutely','hourly','daily','weekly','monthly','yearly') - )) { - throw new \InvalidArgumentException('Unknown value for FREQ=' . strtoupper($value)); - - } - $this->frequency = strtolower($value); - break; - - case 'UNTIL' : - $this->until = DateTimeParser::parse($value); - - // In some cases events are generated with an UNTIL= - // parameter before the actual start of the event. - // - // Not sure why this is happening. We assume that the - // intention was that the event only recurs once. - // - // So we are modifying the parameter so our code doesn't - // break. - if($this->until < $this->baseEvent->DTSTART->getDateTime()) { - $this->until = $this->baseEvent->DTSTART->getDateTime(); - } - break; - - case 'COUNT' : - $this->count = (int)$value; - break; - - case 'INTERVAL' : - $this->interval = (int)$value; - if ($this->interval < 1) { - throw new \InvalidArgumentException('INTERVAL in RRULE must be a positive integer!'); - } - break; - - case 'BYSECOND' : - $this->bySecond = explode(',', $value); - break; - - case 'BYMINUTE' : - $this->byMinute = explode(',', $value); - break; - - case 'BYHOUR' : - $this->byHour = explode(',', $value); - break; - - case 'BYDAY' : - $this->byDay = explode(',', strtoupper($value)); - break; - - case 'BYMONTHDAY' : - $this->byMonthDay = explode(',', $value); - break; - - case 'BYYEARDAY' : - $this->byYearDay = explode(',', $value); - break; - - case 'BYWEEKNO' : - $this->byWeekNo = explode(',', $value); - break; - - case 'BYMONTH' : - $this->byMonth = explode(',', $value); - break; - - case 'BYSETPOS' : - $this->bySetPos = explode(',', $value); - break; - - case 'WKST' : - $this->weekStart = strtoupper($value); - break; - - } - - } - - // Parsing exception dates - if (isset($this->baseEvent->EXDATE)) { - foreach($this->baseEvent->EXDATE as $exDate) { - - foreach(explode(',', (string)$exDate) as $exceptionDate) { - - $this->exceptionDates[] = - DateTimeParser::parse($exceptionDate, $this->startDate->getTimeZone()); - - } - - } - - } - - } - - /** - * Returns the current item in the list - * - * @return DateTime - */ - public function current() { - - if (!$this->valid()) return null; - return clone $this->currentDate; - - } - - /** - * This method returns the startdate for the current iteration of the - * event. - * - * @return DateTime - */ - public function getDtStart() { - - if (!$this->valid()) return null; - return clone $this->currentDate; - - } - - /** - * This method returns the enddate for the current iteration of the - * event. - * - * @return DateTime - */ - public function getDtEnd() { - - if (!$this->valid()) return null; - $dtEnd = clone $this->currentDate; - $dtEnd->add( $this->startDate->diff( $this->endDate ) ); - return clone $dtEnd; - - } - - /** - * Returns a VEVENT object with the updated start and end date. - * - * Any recurrence information is removed, and this function may return an - * 'overridden' event instead. - * - * This method always returns a cloned instance. - * - * @return Component\VEvent - */ - public function getEventObject() { - - if ($this->currentOverriddenEvent) { - return clone $this->currentOverriddenEvent; - } - $event = clone $this->baseEvent; - unset($event->RRULE); - unset($event->EXDATE); - unset($event->RDATE); - unset($event->EXRULE); - - $event->DTSTART->setDateTime($this->getDTStart(), $event->DTSTART->getDateType()); - if (isset($event->DTEND)) { - $event->DTEND->setDateTime($this->getDtEnd(), $event->DTSTART->getDateType()); - } - if ($this->counter > 0) { - $event->{'RECURRENCE-ID'} = (string)$event->DTSTART; - } - - return $event; - - } - - /** - * Returns the current item number - * - * @return int - */ - public function key() { - - return $this->counter; - - } - - /** - * Whether or not there is a 'next item' - * - * @return bool - */ - public function valid() { - - if (!is_null($this->count)) { - return $this->counter < $this->count; - } - if (!is_null($this->until) && $this->currentDate > $this->until) { - - // Need to make sure there's no overridden events past the - // until date. - foreach($this->overriddenEvents as $overriddenEvent) { - - if ($overriddenEvent->DTSTART->getDateTime() >= $this->currentDate) { - - return true; - } - } - return false; - } - return true; - - } - - /** - * Resets the iterator - * - * @return void - */ - public function rewind() { - - $this->currentDate = clone $this->startDate; - $this->counter = 0; - - } - - /** - * This method allows you to quickly go to the next occurrence after the - * specified date. - * - * Note that this checks the current 'endDate', not the 'stardDate'. This - * means that if you forward to January 1st, the iterator will stop at the - * first event that ends *after* January 1st. - * - * @param DateTime $dt - * @return void - */ - public function fastForward(\DateTime $dt) { - - while($this->valid() && $this->getDTEnd() <= $dt) { - $this->next(); - } - - } - - /** - * Returns true if this recurring event never ends. - * - * @return bool - */ - public function isInfinite() { - - return !$this->count && !$this->until; - - } - - /** - * Goes on to the next iteration - * - * @return void - */ - public function next() { - - $previousStamp = $this->currentDate->getTimeStamp(); - - // Finding the next overridden event in line, and storing that for - // later use. - $overriddenEvent = null; - $overriddenDate = null; - $this->currentOverriddenEvent = null; - - foreach($this->overriddenEvents as $index=>$event) { - if ($index > $previousStamp) { - $overriddenEvent = $event; - $overriddenDate = clone $event->DTSTART->getDateTime(); - break; - } - } - - // If we have a stored 'next date', we will use that. - if ($this->nextDate) { - if (!$overriddenDate || $this->nextDate < $overriddenDate) { - $this->currentDate = $this->nextDate; - $currentStamp = $this->currentDate->getTimeStamp(); - $this->nextDate = null; - } else { - $this->currentDate = clone $overriddenDate; - $this->currentOverriddenEvent = $overriddenEvent; - } - $this->counter++; - return; - } - - while(true) { - - // Otherwise, we find the next event in the normal RRULE - // sequence. - switch($this->frequency) { - - case 'hourly' : - $this->nextHourly(); - break; - - case 'daily' : - $this->nextDaily(); - break; - - case 'weekly' : - $this->nextWeekly(); - break; - - case 'monthly' : - $this->nextMonthly(); - break; - - case 'yearly' : - $this->nextYearly(); - break; - - } - $currentStamp = $this->currentDate->getTimeStamp(); - - - // Checking exception dates - foreach($this->exceptionDates as $exceptionDate) { - if ($this->currentDate == $exceptionDate) { - $this->counter++; - continue 2; - } - } - foreach($this->overriddenDates as $check) { - if ($this->currentDate == $check) { - continue 2; - } - } - break; - - } - - - - // Is the date we have actually higher than the next overiddenEvent? - if ($overriddenDate && $this->currentDate > $overriddenDate) { - $this->nextDate = clone $this->currentDate; - $this->currentDate = clone $overriddenDate; - $this->currentOverriddenEvent = $overriddenEvent; - $this->handledOverridden++; - } - $this->counter++; - - - /* - * If we have overridden events left in the queue, but our counter is - * running out, we should grab one of those. - */ - if (!is_null($overriddenEvent) && !is_null($this->count) && count($this->overriddenEvents) - $this->handledOverridden >= ($this->count - $this->counter)) { - - $this->currentOverriddenEvent = $overriddenEvent; - $this->currentDate = clone $overriddenDate; - $this->handledOverridden++; - - } - - } - - /** - * Does the processing for advancing the iterator for hourly frequency. - * - * @return void - */ - protected function nextHourly() { - - if (!$this->byHour) { - $this->currentDate->modify('+' . $this->interval . ' hours'); - return; - } - } - - /** - * Does the processing for advancing the iterator for daily frequency. - * - * @return void - */ - protected function nextDaily() { - - if (!$this->byHour && !$this->byDay) { - $this->currentDate->modify('+' . $this->interval . ' days'); - return; - } - - if (isset($this->byHour)) { - $recurrenceHours = $this->getHours(); - } - - if (isset($this->byDay)) { - $recurrenceDays = $this->getDays(); - } - - do { - - if ($this->byHour) { - if ($this->currentDate->format('G') == '23') { - // to obey the interval rule - $this->currentDate->modify('+' . $this->interval-1 . ' days'); - } - - $this->currentDate->modify('+1 hours'); - - } else { - $this->currentDate->modify('+' . $this->interval . ' days'); - - } - - // Current day of the week - $currentDay = $this->currentDate->format('w'); - - // Current hour of the day - $currentHour = $this->currentDate->format('G'); - - } while (($this->byDay && !in_array($currentDay, $recurrenceDays)) || ($this->byHour && !in_array($currentHour, $recurrenceHours))); - - } - - /** - * Does the processing for advancing the iterator for weekly frequency. - * - * @return void - */ - protected function nextWeekly() { - - if (!$this->byHour && !$this->byDay) { - $this->currentDate->modify('+' . $this->interval . ' weeks'); - return; - } - - if ($this->byHour) { - $recurrenceHours = $this->getHours(); - } - - if ($this->byDay) { - $recurrenceDays = $this->getDays(); - } - - // First day of the week: - $firstDay = $this->dayMap[$this->weekStart]; - - do { - - if ($this->byHour) { - $this->currentDate->modify('+1 hours'); - } else { - $this->currentDate->modify('+1 days'); - } - - // Current day of the week - $currentDay = (int) $this->currentDate->format('w'); - - // Current hour of the day - $currentHour = (int) $this->currentDate->format('G'); - - // We need to roll over to the next week - if ($currentDay === $firstDay && (!$this->byHour || $currentHour == '0')) { - $this->currentDate->modify('+' . $this->interval-1 . ' weeks'); - - // We need to go to the first day of this week, but only if we - // are not already on this first day of this week. - if($this->currentDate->format('w') != $firstDay) { - $this->currentDate->modify('last ' . $this->dayNames[$this->dayMap[$this->weekStart]]); - } - } - - // We have a match - } while (($this->byDay && !in_array($currentDay, $recurrenceDays)) || ($this->byHour && !in_array($currentHour, $recurrenceHours))); - } - - /** - * Does the processing for advancing the iterator for monthly frequency. - * - * @return void - */ - protected function nextMonthly() { - - $currentDayOfMonth = $this->currentDate->format('j'); - if (!$this->byMonthDay && !$this->byDay) { - - // If the current day is higher than the 28th, rollover can - // occur to the next month. We Must skip these invalid - // entries. - if ($currentDayOfMonth < 29) { - $this->currentDate->modify('+' . $this->interval . ' months'); - } else { - $increase = 0; - do { - $increase++; - $tempDate = clone $this->currentDate; - $tempDate->modify('+ ' . ($this->interval*$increase) . ' months'); - } while ($tempDate->format('j') != $currentDayOfMonth); - $this->currentDate = $tempDate; - } - return; - } - - while(true) { - - $occurrences = $this->getMonthlyOccurrences(); - - foreach($occurrences as $occurrence) { - - // The first occurrence thats higher than the current - // day of the month wins. - if ($occurrence > $currentDayOfMonth) { - break 2; - } - - } - - // If we made it all the way here, it means there were no - // valid occurrences, and we need to advance to the next - // month. - $this->currentDate->modify('first day of this month'); - $this->currentDate->modify('+ ' . $this->interval . ' months'); - - // This goes to 0 because we need to start counting at hte - // beginning. - $currentDayOfMonth = 0; - - } - - $this->currentDate->setDate($this->currentDate->format('Y'), $this->currentDate->format('n'), $occurrence); - - } - - /** - * Does the processing for advancing the iterator for yearly frequency. - * - * @return void - */ - protected function nextYearly() { - - $currentMonth = $this->currentDate->format('n'); - $currentYear = $this->currentDate->format('Y'); - $currentDayOfMonth = $this->currentDate->format('j'); - - // No sub-rules, so we just advance by year - if (!$this->byMonth) { - - // Unless it was a leap day! - if ($currentMonth==2 && $currentDayOfMonth==29) { - - $counter = 0; - do { - $counter++; - // Here we increase the year count by the interval, until - // we hit a date that's also in a leap year. - // - // We could just find the next interval that's dividable by - // 4, but that would ignore the rule that there's no leap - // year every year that's dividable by a 100, but not by - // 400. (1800, 1900, 2100). So we just rely on the datetime - // functions instead. - $nextDate = clone $this->currentDate; - $nextDate->modify('+ ' . ($this->interval*$counter) . ' years'); - } while ($nextDate->format('n')!=2); - $this->currentDate = $nextDate; - - return; - - } - - // The easiest form - $this->currentDate->modify('+' . $this->interval . ' years'); - return; - - } - - $currentMonth = $this->currentDate->format('n'); - $currentYear = $this->currentDate->format('Y'); - $currentDayOfMonth = $this->currentDate->format('j'); - - $advancedToNewMonth = false; - - // If we got a byDay or getMonthDay filter, we must first expand - // further. - if ($this->byDay || $this->byMonthDay) { - - while(true) { - - $occurrences = $this->getMonthlyOccurrences(); - - foreach($occurrences as $occurrence) { - - // The first occurrence that's higher than the current - // day of the month wins. - // If we advanced to the next month or year, the first - // occurrence is always correct. - if ($occurrence > $currentDayOfMonth || $advancedToNewMonth) { - break 2; - } - - } - - // If we made it here, it means we need to advance to - // the next month or year. - $currentDayOfMonth = 1; - $advancedToNewMonth = true; - do { - - $currentMonth++; - if ($currentMonth>12) { - $currentYear+=$this->interval; - $currentMonth = 1; - } - } while (!in_array($currentMonth, $this->byMonth)); - - $this->currentDate->setDate($currentYear, $currentMonth, $currentDayOfMonth); - - } - - // If we made it here, it means we got a valid occurrence - $this->currentDate->setDate($currentYear, $currentMonth, $occurrence); - return; - - } else { - - // These are the 'byMonth' rules, if there are no byDay or - // byMonthDay sub-rules. - do { - - $currentMonth++; - if ($currentMonth>12) { - $currentYear+=$this->interval; - $currentMonth = 1; - } - } while (!in_array($currentMonth, $this->byMonth)); - $this->currentDate->setDate($currentYear, $currentMonth, $currentDayOfMonth); - - return; - - } - - } - - /** - * Returns all the occurrences for a monthly frequency with a 'byDay' or - * 'byMonthDay' expansion for the current month. - * - * The returned list is an array of integers with the day of month (1-31). - * - * @return array - */ - protected function getMonthlyOccurrences() { - - $startDate = clone $this->currentDate; - - $byDayResults = array(); - - // Our strategy is to simply go through the byDays, advance the date to - // that point and add it to the results. - if ($this->byDay) foreach($this->byDay as $day) { - - $dayName = $this->dayNames[$this->dayMap[substr($day,-2)]]; - - // Dayname will be something like 'wednesday'. Now we need to find - // all wednesdays in this month. - $dayHits = array(); - - $checkDate = clone $startDate; - $checkDate->modify('first day of this month'); - $checkDate->modify($dayName); - - do { - $dayHits[] = $checkDate->format('j'); - $checkDate->modify('next ' . $dayName); - } while ($checkDate->format('n') === $startDate->format('n')); - - // So now we have 'all wednesdays' for month. It is however - // possible that the user only really wanted the 1st, 2nd or last - // wednesday. - if (strlen($day)>2) { - $offset = (int)substr($day,0,-2); - - if ($offset>0) { - // It is possible that the day does not exist, such as a - // 5th or 6th wednesday of the month. - if (isset($dayHits[$offset-1])) { - $byDayResults[] = $dayHits[$offset-1]; - } - } else { - - // if it was negative we count from the end of the array - $byDayResults[] = $dayHits[count($dayHits) + $offset]; - } - } else { - // There was no counter (first, second, last wednesdays), so we - // just need to add the all to the list). - $byDayResults = array_merge($byDayResults, $dayHits); - - } - - } - - $byMonthDayResults = array(); - if ($this->byMonthDay) foreach($this->byMonthDay as $monthDay) { - - // Removing values that are out of range for this month - if ($monthDay > $startDate->format('t') || - $monthDay < 0-$startDate->format('t')) { - continue; - } - if ($monthDay>0) { - $byMonthDayResults[] = $monthDay; - } else { - // Negative values - $byMonthDayResults[] = $startDate->format('t') + 1 + $monthDay; - } - } - - // If there was just byDay or just byMonthDay, they just specify our - // (almost) final list. If both were provided, then byDay limits the - // list. - if ($this->byMonthDay && $this->byDay) { - $result = array_intersect($byMonthDayResults, $byDayResults); - } elseif ($this->byMonthDay) { - $result = $byMonthDayResults; - } else { - $result = $byDayResults; - } - $result = array_unique($result); - sort($result, SORT_NUMERIC); - - // The last thing that needs checking is the BYSETPOS. If it's set, it - // means only certain items in the set survive the filter. - if (!$this->bySetPos) { - return $result; - } - - $filteredResult = array(); - foreach($this->bySetPos as $setPos) { - - if ($setPos<0) { - $setPos = count($result)-($setPos+1); - } - if (isset($result[$setPos-1])) { - $filteredResult[] = $result[$setPos-1]; - } - } - - sort($filteredResult, SORT_NUMERIC); - return $filteredResult; - - } - - protected function getHours() - { - $recurrenceHours = array(); - foreach($this->byHour as $byHour) { - $recurrenceHours[] = $byHour; - } - - return $recurrenceHours; - } - - protected function getDays() - { - $recurrenceDays = array(); - foreach($this->byDay as $byDay) { - - // The day may be preceeded with a positive (+n) or - // negative (-n) integer. However, this does not make - // sense in 'weekly' so we ignore it here. - $recurrenceDays[] = $this->dayMap[substr($byDay,-2)]; - - } - - return $recurrenceDays; - } -} -
--- a/plugins/libcalendaring/lib/Sabre/VObject/Splitter/ICalendar.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,111 +0,0 @@ -<?php - -namespace Sabre\VObject\Splitter; - -use Sabre\VObject; - -/** - * Splitter - * - * This class is responsible for splitting up iCalendar objects. - * - * This class expects a single VCALENDAR object with one or more - * calendar-objects inside. Objects with identical UID's will be combined into - * a single object. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Dominik Tobschall - * @author Armin Hackmann - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class ICalendar implements SplitterInterface { - - /** - * Timezones - * - * @var array - */ - protected $vtimezones = array(); - - /** - * iCalendar objects - * - * @var array - */ - protected $objects = array(); - - /** - * Constructor - * - * The splitter should receive an readable file stream as it's input. - * - * @param resource $input - */ - public function __construct($input) { - - $data = VObject\Reader::read(stream_get_contents($input)); - $vtimezones = array(); - $components = array(); - - foreach($data->children as $component) { - if (!$component instanceof VObject\Component) { - continue; - } - - // Get all timezones - if ($component->name === 'VTIMEZONE') { - $this->vtimezones[(string)$component->TZID] = $component; - continue; - } - - // Get component UID for recurring Events search - if($component->UID) { - $uid = (string)$component->UID; - } else { - // Generating a random UID - $uid = sha1(microtime()) . '-vobjectimport'; - } - - // Take care of recurring events - if (!array_key_exists($uid, $this->objects)) { - $this->objects[$uid] = VObject\Component::create('VCALENDAR'); - } - - $this->objects[$uid]->add(clone $component); - } - - } - - /** - * Every time getNext() is called, a new object will be parsed, until we - * hit the end of the stream. - * - * When the end is reached, null will be returned. - * - * @return Sabre\VObject\Component|null - */ - public function getNext() { - - if($object=array_shift($this->objects)) { - - // create our baseobject - $object->version = '2.0'; - $object->prodid = '-//Sabre//Sabre VObject ' . VObject\Version::VERSION . '//EN'; - $object->calscale = 'GREGORIAN'; - - // add vtimezone information to obj (if we have it) - foreach ($this->vtimezones as $vtimezone) { - $object->add($vtimezone); - } - - return $object; - - } else { - - return null; - - } - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Splitter/SplitterInterface.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,39 +0,0 @@ -<?php - -namespace Sabre\VObject\Splitter; - -/** - * VObject splitter - * - * The splitter is responsible for reading a large vCard or iCalendar object, - * and splitting it into multiple objects. - * - * This is for example for Card and CalDAV, which require every event and vcard - * to exist in their own objects, instead of one large one. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Dominik Tobschall - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -interface SplitterInterface { - - /** - * Constructor - * - * The splitter should receive an readable file stream as it's input. - * - * @param resource $input - */ - function __construct($input); - - /** - * Every time getNext() is called, a new object will be parsed, until we - * hit the end of the stream. - * - * When the end is reached, null will be returned. - * - * @return Sabre\VObject\Component|null - */ - function getNext(); - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Splitter/VCard.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,76 +0,0 @@ -<?php - -namespace Sabre\VObject\Splitter; - -use Sabre\VObject; - -/** - * Splitter - * - * This class is responsible for splitting up VCard objects. - * - * It is assumed that the input stream contains 1 or more VCARD objects. This - * class checks for BEGIN:VCARD and END:VCARD and parses each encountered - * component individually. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Dominik Tobschall - * @author Armin Hackmann - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class VCard implements SplitterInterface { - - /** - * File handle - * - * @var resource - */ - protected $input; - - /** - * Constructor - * - * The splitter should receive an readable file stream as it's input. - * - * @param resource $input - */ - public function __construct($input) { - - $this->input = $input; - - } - - /** - * Every time getNext() is called, a new object will be parsed, until we - * hit the end of the stream. - * - * When the end is reached, null will be returned. - * - * @return Sabre\VObject\Component|null - */ - public function getNext() { - - $vcard = ''; - - do { - - if (feof($this->input)) { - return false; - } - - $line = fgets($this->input); - $vcard .= $line; - - } while(strtoupper(substr($line,0,4))!=="END:"); - - $object = VObject\Reader::read($vcard); - - if($object->name !== 'VCARD') { - throw new \InvalidArgumentException("Thats no vCard!", 1); - } - - return $object; - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/StringUtil.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,61 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Useful utilities for working with various strings. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class StringUtil { - - /** - * Returns true or false depending on if a string is valid UTF-8 - * - * @param string $str - * @return bool - */ - static function isUTF8($str) { - - // First check.. mb_check_encoding - if (!mb_check_encoding($str, 'UTF-8')) { - return false; - } - - // Control characters - if (preg_match('%(?:[\x00-\x08\x0B-\x0C\x0E\x0F])%', $str)) { - return false; - } - - return true; - - } - - /** - * This method tries its best to convert the input string to UTF-8. - * - * Currently only ISO-5991-1 input and UTF-8 input is supported, but this - * may be expanded upon if we receive other examples. - * - * @param string $str - * @return string - */ - static function convertToUTF8($str) { - - $encoding = mb_detect_encoding($str , array('UTF-8','ISO-8859-1'), true); - - if ($encoding === 'ISO-8859-1') { - $newStr = utf8_encode($str); - } else { - $newStr = $str; - } - - // Removing any control characters - return (preg_replace('%(?:[\x00-\x08\x0B-\x0C\x0E\x0F])%', '', $newStr)); - - } - -} -
--- a/plugins/libcalendaring/lib/Sabre/VObject/TimeZoneUtil.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,482 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Time zone name translation - * - * This file translates well-known time zone names into "Olson database" time zone names. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Frank Edelhaeuser (fedel@users.sourceforge.net) - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class TimeZoneUtil { - - public static $map = array( - - // from http://unicode.org/repos/cldr-tmp/trunk/diff/supplemental/zone_tzid.html - // snapshot taken on 2012/01/16 - - // windows - 'AUS Central Standard Time'=>'Australia/Darwin', - 'AUS Eastern Standard Time'=>'Australia/Sydney', - 'Afghanistan Standard Time'=>'Asia/Kabul', - 'Alaskan Standard Time'=>'America/Anchorage', - 'Arab Standard Time'=>'Asia/Riyadh', - 'Arabian Standard Time'=>'Asia/Dubai', - 'Arabic Standard Time'=>'Asia/Baghdad', - 'Argentina Standard Time'=>'America/Buenos_Aires', - 'Armenian Standard Time'=>'Asia/Yerevan', - 'Atlantic Standard Time'=>'America/Halifax', - 'Azerbaijan Standard Time'=>'Asia/Baku', - 'Azores Standard Time'=>'Atlantic/Azores', - 'Bangladesh Standard Time'=>'Asia/Dhaka', - 'Canada Central Standard Time'=>'America/Regina', - 'Cape Verde Standard Time'=>'Atlantic/Cape_Verde', - 'Caucasus Standard Time'=>'Asia/Yerevan', - 'Cen. Australia Standard Time'=>'Australia/Adelaide', - 'Central America Standard Time'=>'America/Guatemala', - 'Central Asia Standard Time'=>'Asia/Almaty', - 'Central Brazilian Standard Time'=>'America/Cuiaba', - 'Central Europe Standard Time'=>'Europe/Budapest', - 'Central European Standard Time'=>'Europe/Warsaw', - 'Central Pacific Standard Time'=>'Pacific/Guadalcanal', - 'Central Standard Time'=>'America/Chicago', - 'Central Standard Time (Mexico)'=>'America/Mexico_City', - 'China Standard Time'=>'Asia/Shanghai', - 'Dateline Standard Time'=>'Etc/GMT+12', - 'E. Africa Standard Time'=>'Africa/Nairobi', - 'E. Australia Standard Time'=>'Australia/Brisbane', - 'E. Europe Standard Time'=>'Europe/Minsk', - 'E. South America Standard Time'=>'America/Sao_Paulo', - 'Eastern Standard Time'=>'America/New_York', - 'Egypt Standard Time'=>'Africa/Cairo', - 'Ekaterinburg Standard Time'=>'Asia/Yekaterinburg', - 'FLE Standard Time'=>'Europe/Kiev', - 'Fiji Standard Time'=>'Pacific/Fiji', - 'GMT Standard Time'=>'Europe/London', - 'GTB Standard Time'=>'Europe/Istanbul', - 'Georgian Standard Time'=>'Asia/Tbilisi', - 'Greenland Standard Time'=>'America/Godthab', - 'Greenwich Standard Time'=>'Atlantic/Reykjavik', - 'Hawaiian Standard Time'=>'Pacific/Honolulu', - 'India Standard Time'=>'Asia/Calcutta', - 'Iran Standard Time'=>'Asia/Tehran', - 'Israel Standard Time'=>'Asia/Jerusalem', - 'Jordan Standard Time'=>'Asia/Amman', - 'Kamchatka Standard Time'=>'Asia/Kamchatka', - 'Korea Standard Time'=>'Asia/Seoul', - 'Magadan Standard Time'=>'Asia/Magadan', - 'Mauritius Standard Time'=>'Indian/Mauritius', - 'Mexico Standard Time'=>'America/Mexico_City', - 'Mexico Standard Time 2'=>'America/Chihuahua', - 'Mid-Atlantic Standard Time'=>'Etc/GMT-2', - 'Middle East Standard Time'=>'Asia/Beirut', - 'Montevideo Standard Time'=>'America/Montevideo', - 'Morocco Standard Time'=>'Africa/Casablanca', - 'Mountain Standard Time'=>'America/Denver', - 'Mountain Standard Time (Mexico)'=>'America/Chihuahua', - 'Myanmar Standard Time'=>'Asia/Rangoon', - 'N. Central Asia Standard Time'=>'Asia/Novosibirsk', - 'Namibia Standard Time'=>'Africa/Windhoek', - 'Nepal Standard Time'=>'Asia/Katmandu', - 'New Zealand Standard Time'=>'Pacific/Auckland', - 'Newfoundland Standard Time'=>'America/St_Johns', - 'North Asia East Standard Time'=>'Asia/Irkutsk', - 'North Asia Standard Time'=>'Asia/Krasnoyarsk', - 'Pacific SA Standard Time'=>'America/Santiago', - 'Pacific Standard Time'=>'America/Los_Angeles', - 'Pacific Standard Time (Mexico)'=>'America/Santa_Isabel', - 'Pakistan Standard Time'=>'Asia/Karachi', - 'Paraguay Standard Time'=>'America/Asuncion', - 'Romance Standard Time'=>'Europe/Paris', - 'Russian Standard Time'=>'Europe/Moscow', - 'SA Eastern Standard Time'=>'America/Cayenne', - 'SA Pacific Standard Time'=>'America/Bogota', - 'SA Western Standard Time'=>'America/La_Paz', - 'SE Asia Standard Time'=>'Asia/Bangkok', - 'Samoa Standard Time'=>'Pacific/Apia', - 'Singapore Standard Time'=>'Asia/Singapore', - 'South Africa Standard Time'=>'Africa/Johannesburg', - 'Sri Lanka Standard Time'=>'Asia/Colombo', - 'Syria Standard Time'=>'Asia/Damascus', - 'Taipei Standard Time'=>'Asia/Taipei', - 'Tasmania Standard Time'=>'Australia/Hobart', - 'Tokyo Standard Time'=>'Asia/Tokyo', - 'Tonga Standard Time'=>'Pacific/Tongatapu', - 'US Eastern Standard Time'=>'America/Indianapolis', - 'US Mountain Standard Time'=>'America/Phoenix', - 'UTC+12'=>'Etc/GMT-12', - 'UTC-02'=>'Etc/GMT+2', - 'UTC-11'=>'Etc/GMT+11', - 'Ulaanbaatar Standard Time'=>'Asia/Ulaanbaatar', - 'Venezuela Standard Time'=>'America/Caracas', - 'Vladivostok Standard Time'=>'Asia/Vladivostok', - 'W. Australia Standard Time'=>'Australia/Perth', - 'W. Central Africa Standard Time'=>'Africa/Lagos', - 'W. Europe Standard Time'=>'Europe/Berlin', - 'West Asia Standard Time'=>'Asia/Tashkent', - 'West Pacific Standard Time'=>'Pacific/Port_Moresby', - 'Yakutsk Standard Time'=>'Asia/Yakutsk', - - // Microsoft exchange timezones - // Source: - // http://msdn.microsoft.com/en-us/library/ms988620%28v=exchg.65%29.aspx - // - // Correct timezones deduced with help from: - // http://en.wikipedia.org/wiki/List_of_tz_database_time_zones - 'Universal Coordinated Time' => 'UTC', - 'Casablanca, Monrovia' => 'Africa/Casablanca', - 'Greenwich Mean Time: Dublin, Edinburgh, Lisbon, London' => 'Europe/Lisbon', - 'Greenwich Mean Time; Dublin, Edinburgh, London' => 'Europe/London', - 'Amsterdam, Berlin, Bern, Rome, Stockholm, Vienna' => 'Europe/Berlin', - 'Belgrade, Pozsony, Budapest, Ljubljana, Prague' => 'Europe/Prague', - 'Brussels, Copenhagen, Madrid, Paris' => 'Europe/Paris', - 'Paris, Madrid, Brussels, Copenhagen' => 'Europe/Paris', - 'Prague, Central Europe' => 'Europe/Prague', - 'Sarajevo, Skopje, Sofija, Vilnius, Warsaw, Zagreb' => 'Europe/Sarajevo', - 'West Central Africa' => 'Africa/Luanda', // This was a best guess - 'Athens, Istanbul, Minsk' => 'Europe/Athens', - 'Bucharest' => 'Europe/Bucharest', - 'Cairo' => 'Africa/Cairo', - 'Harare, Pretoria' => 'Africa/Harare', - 'Helsinki, Riga, Tallinn' => 'Europe/Helsinki', - 'Israel, Jerusalem Standard Time' => 'Asia/Jerusalem', - 'Baghdad' => 'Asia/Baghdad', - 'Arab, Kuwait, Riyadh' => 'Asia/Kuwait', - 'Moscow, St. Petersburg, Volgograd' => 'Europe/Moscow', - 'East Africa, Nairobi' => 'Africa/Nairobi', - 'Tehran' => 'Asia/Tehran', - 'Abu Dhabi, Muscat' => 'Asia/Muscat', // Best guess - 'Baku, Tbilisi, Yerevan' => 'Asia/Baku', - 'Kabul' => 'Asia/Kabul', - 'Ekaterinburg' => 'Asia/Yekaterinburg', - 'Islamabad, Karachi, Tashkent' => 'Asia/Karachi', - 'Kolkata, Chennai, Mumbai, New Delhi, India Standard Time' => 'Asia/Calcutta', - 'Kathmandu, Nepal' => 'Asia/Kathmandu', - 'Almaty, Novosibirsk, North Central Asia' => 'Asia/Almaty', - 'Astana, Dhaka' => 'Asia/Dhaka', - 'Sri Jayawardenepura, Sri Lanka' => 'Asia/Colombo', - 'Rangoon' => 'Asia/Rangoon', - 'Bangkok, Hanoi, Jakarta' => 'Asia/Bangkok', - 'Krasnoyarsk' => 'Asia/Krasnoyarsk', - 'Beijing, Chongqing, Hong Kong SAR, Urumqi' => 'Asia/Shanghai', - 'Irkutsk, Ulaan Bataar' => 'Asia/Irkutsk', - 'Kuala Lumpur, Singapore' => 'Asia/Singapore', - 'Perth, Western Australia' => 'Australia/Perth', - 'Taipei' => 'Asia/Taipei', - 'Osaka, Sapporo, Tokyo' => 'Asia/Tokyo', - 'Seoul, Korea Standard time' => 'Asia/Seoul', - 'Yakutsk' => 'Asia/Yakutsk', - 'Adelaide, Central Australia' => 'Australia/Adelaide', - 'Darwin' => 'Australia/Darwin', - 'Brisbane, East Australia' => 'Australia/Brisbane', - 'Canberra, Melbourne, Sydney, Hobart (year 2000 only)' => 'Australia/Sydney', - 'Guam, Port Moresby' => 'Pacific/Guam', - 'Hobart, Tasmania' => 'Australia/Hobart', - 'Vladivostok' => 'Asia/Vladivostok', - 'Magadan, Solomon Is., New Caledonia' => 'Asia/Magadan', - 'Auckland, Wellington' => 'Pacific/Auckland', - 'Fiji Islands, Kamchatka, Marshall Is.' => 'Pacific/Fiji', - 'Nuku\'alofa, Tonga' => 'Pacific/Tongatapu', - 'Azores' => 'Atlantic/Azores', - 'Cape Verde Is.' => 'Atlantic/Cape_Verde', - 'Mid-Atlantic' => 'America/Noronha', - 'Brasilia' => 'America/Sao_Paulo', // Best guess - 'Buenos Aires' => 'America/Argentina/Buenos_Aires', - 'Greenland' => 'America/Godthab', - 'Newfoundland' => 'America/St_Johns', - 'Atlantic Time (Canada)' => 'America/Halifax', - 'Caracas, La Paz' => 'America/Caracas', - 'Santiago' => 'America/Santiago', - 'Bogota, Lima, Quito' => 'America/Bogota', - 'Eastern Time (US & Canada)' => 'America/New_York', - 'Indiana (East)' => 'America/Indiana/Indianapolis', - 'Central America' => 'America/Guatemala', - 'Central Time (US & Canada)' => 'America/Chicago', - 'Mexico City, Tegucigalpa' => 'America/Mexico_City', - 'Saskatchewan' => 'America/Edmonton', - 'Arizona' => 'America/Phoenix', - 'Mountain Time (US & Canada)' => 'America/Denver', // Best guess - 'Pacific Time (US & Canada); Tijuana' => 'America/Los_Angeles', // Best guess - 'Alaska' => 'America/Anchorage', - 'Hawaii' => 'Pacific/Honolulu', - 'Midway Island, Samoa' => 'Pacific/Midway', - 'Eniwetok, Kwajalein, Dateline Time' => 'Pacific/Kwajalein', - - // The following list are timezone names that could be generated by - // Lotus / Domino - 'Dateline' => 'Etc/GMT-12', - 'Samoa' => 'Pacific/Apia', - 'Hawaiian' => 'Pacific/Honolulu', - 'Alaskan' => 'America/Anchorage', - 'Pacific' => 'America/Los_Angeles', - 'Pacific Standard Time' => 'America/Los_Angeles', - 'Mexico Standard Time 2' => 'America/Chihuahua', - 'Mountain' => 'America/Denver', - 'Mountain Standard Time' => 'America/Chihuahua', - 'US Mountain' => 'America/Phoenix', - 'Canada Central' => 'America/Edmonton', - 'Central America' => 'America/Guatemala', - 'Central' => 'America/Chicago', - 'Central Standard Time' => 'America/Mexico_City', - 'Mexico' => 'America/Mexico_City', - 'Eastern' => 'America/New_York', - 'SA Pacific' => 'America/Bogota', - 'US Eastern' => 'America/Indiana/Indianapolis', - 'Venezuela' => 'America/Caracas', - 'Atlantic' => 'America/Halifax', - 'Central Brazilian' => 'America/Manaus', - 'Pacific SA' => 'America/Santiago', - 'SA Western' => 'America/La_Paz', - 'Newfoundland' => 'America/St_Johns', - 'Argentina' => 'America/Argentina/Buenos_Aires', - 'E. South America' => 'America/Belem', - 'Greenland' => 'America/Godthab', - 'Montevideo' => 'America/Montevideo', - 'SA Eastern' => 'America/Belem', - 'Mid-Atlantic' => 'Etc/GMT-2', - 'Azores' => 'Atlantic/Azores', - 'Cape Verde' => 'Atlantic/Cape_Verde', - 'Greenwich' => 'Atlantic/Reykjavik', // No I'm serious.. Greenwich is not GMT. - 'Morocco' => 'Africa/Casablanca', - 'Central Europe' => 'Europe/Prague', - 'Central European' => 'Europe/Sarajevo', - 'Romance' => 'Europe/Paris', - 'W. Central Africa' => 'Africa/Lagos', // Best guess - 'W. Europe' => 'Europe/Amsterdam', - 'E. Europe' => 'Europe/Minsk', - 'Egypt' => 'Africa/Cairo', - 'FLE' => 'Europe/Helsinki', - 'GTB' => 'Europe/Athens', - 'Israel' => 'Asia/Jerusalem', - 'Jordan' => 'Asia/Amman', - 'Middle East' => 'Asia/Beirut', - 'Namibia' => 'Africa/Windhoek', - 'South Africa' => 'Africa/Harare', - 'Arab' => 'Asia/Kuwait', - 'Arabic' => 'Asia/Baghdad', - 'E. Africa' => 'Africa/Nairobi', - 'Georgian' => 'Asia/Tbilisi', - 'Russian' => 'Europe/Moscow', - 'Iran' => 'Asia/Tehran', - 'Arabian' => 'Asia/Muscat', - 'Armenian' => 'Asia/Yerevan', - 'Azerbijan' => 'Asia/Baku', - 'Caucasus' => 'Asia/Yerevan', - 'Mauritius' => 'Indian/Mauritius', - 'Afghanistan' => 'Asia/Kabul', - 'Ekaterinburg' => 'Asia/Yekaterinburg', - 'Pakistan' => 'Asia/Karachi', - 'West Asia' => 'Asia/Tashkent', - 'India' => 'Asia/Calcutta', - 'Sri Lanka' => 'Asia/Colombo', - 'Nepal' => 'Asia/Kathmandu', - 'Central Asia' => 'Asia/Dhaka', - 'N. Central Asia' => 'Asia/Almaty', - 'Myanmar' => 'Asia/Rangoon', - 'North Asia' => 'Asia/Krasnoyarsk', - 'SE Asia' => 'Asia/Bangkok', - 'China' => 'Asia/Shanghai', - 'North Asia East' => 'Asia/Irkutsk', - 'Singapore' => 'Asia/Singapore', - 'Taipei' => 'Asia/Taipei', - 'W. Australia' => 'Australia/Perth', - 'Korea' => 'Asia/Seoul', - 'Tokyo' => 'Asia/Tokyo', - 'Yakutsk' => 'Asia/Yakutsk', - 'AUS Central' => 'Australia/Darwin', - 'Cen. Australia' => 'Australia/Adelaide', - 'AUS Eastern' => 'Australia/Sydney', - 'E. Australia' => 'Australia/Brisbane', - 'Tasmania' => 'Australia/Hobart', - 'Vladivostok' => 'Asia/Vladivostok', - 'West Pacific' => 'Pacific/Guam', - 'Central Pacific' => 'Asia/Magadan', - 'Fiji' => 'Pacific/Fiji', - 'New Zealand' => 'Pacific/Auckland', - 'Tonga' => 'Pacific/Tongatapu', - ); - - /** - * List of microsoft exchange timezone ids. - * - * Source: http://msdn.microsoft.com/en-us/library/aa563018(loband).aspx - */ - public static $microsoftExchangeMap = array( - 0 => 'UTC', - 31 => 'Africa/Casablanca', - - // Insanely, id #2 is used for both Europe/Lisbon, and Europe/Sarajevo. - // I'm not even kidding.. We handle this special case in the - // getTimeZone method. - 2 => 'Europe/Lisbon', - 1 => 'Europe/London', - 4 => 'Europe/Berlin', - 6 => 'Europe/Prague', - 3 => 'Europe/Paris', - 69 => 'Africa/Luanda', // This was a best guess - 7 => 'Europe/Athens', - 5 => 'Europe/Bucharest', - 49 => 'Africa/Cairo', - 50 => 'Africa/Harare', - 59 => 'Europe/Helsinki', - 27 => 'Asia/Jerusalem', - 26 => 'Asia/Baghdad', - 74 => 'Asia/Kuwait', - 51 => 'Europe/Moscow', - 56 => 'Africa/Nairobi', - 25 => 'Asia/Tehran', - 24 => 'Asia/Muscat', // Best guess - 54 => 'Asia/Baku', - 48 => 'Asia/Kabul', - 58 => 'Asia/Yekaterinburg', - 47 => 'Asia/Karachi', - 23 => 'Asia/Calcutta', - 62 => 'Asia/Kathmandu', - 46 => 'Asia/Almaty', - 71 => 'Asia/Dhaka', - 66 => 'Asia/Colombo', - 61 => 'Asia/Rangoon', - 22 => 'Asia/Bangkok', - 64 => 'Asia/Krasnoyarsk', - 45 => 'Asia/Shanghai', - 63 => 'Asia/Irkutsk', - 21 => 'Asia/Singapore', - 73 => 'Australia/Perth', - 75 => 'Asia/Taipei', - 20 => 'Asia/Tokyo', - 72 => 'Asia/Seoul', - 70 => 'Asia/Yakutsk', - 19 => 'Australia/Adelaide', - 44 => 'Australia/Darwin', - 18 => 'Australia/Brisbane', - 76 => 'Australia/Sydney', - 43 => 'Pacific/Guam', - 42 => 'Australia/Hobart', - 68 => 'Asia/Vladivostok', - 41 => 'Asia/Magadan', - 17 => 'Pacific/Auckland', - 40 => 'Pacific/Fiji', - 67 => 'Pacific/Tongatapu', - 29 => 'Atlantic/Azores', - 53 => 'Atlantic/Cape_Verde', - 30 => 'America/Noronha', - 8 => 'America/Sao_Paulo', // Best guess - 32 => 'America/Argentina/Buenos_Aires', - 60 => 'America/Godthab', - 28 => 'America/St_Johns', - 9 => 'America/Halifax', - 33 => 'America/Caracas', - 65 => 'America/Santiago', - 35 => 'America/Bogota', - 10 => 'America/New_York', - 34 => 'America/Indiana/Indianapolis', - 55 => 'America/Guatemala', - 11 => 'America/Chicago', - 37 => 'America/Mexico_City', - 36 => 'America/Edmonton', - 38 => 'America/Phoenix', - 12 => 'America/Denver', // Best guess - 13 => 'America/Los_Angeles', // Best guess - 14 => 'America/Anchorage', - 15 => 'Pacific/Honolulu', - 16 => 'Pacific/Midway', - 39 => 'Pacific/Kwajalein', - ); - - /** - * This method will try to find out the correct timezone for an iCalendar - * date-time value. - * - * You must pass the contents of the TZID parameter, as well as the full - * calendar. - * - * If the lookup fails, this method will return the default PHP timezone - * (as configured using date_default_timezone_set, or the date.timezone ini - * setting). - * - * Alternatively, if $failIfUncertain is set to true, it will throw an - * exception if we cannot accurately determine the timezone. - * - * @param string $tzid - * @param Sabre\VObject\Component $vcalendar - * @return DateTimeZone - */ - static public function getTimeZone($tzid, Component $vcalendar = null, $failIfUncertain = false) { - - // First we will just see if the tzid is a support timezone identifier. - try { - return new \DateTimeZone($tzid); - } catch (\Exception $e) { - } - - // Next, we check if the tzid is somewhere in our tzid map. - if (isset(self::$map[$tzid])) { - return new \DateTimeZone(self::$map[$tzid]); - } - - // Maybe the author was hyper-lazy and just included an offset. We - // support it, but we aren't happy about it. - if (preg_match('/^GMT(\+|-)([0-9]{4})$/', $tzid, $matches)) { - return new \DateTimeZone('Etc/GMT' . $matches[1] . ltrim(substr($matches[2],0,2),'0')); - } - - if ($vcalendar) { - - // If that didn't work, we will scan VTIMEZONE objects - foreach($vcalendar->select('VTIMEZONE') as $vtimezone) { - - if ((string)$vtimezone->TZID === $tzid) { - - // Some clients add 'X-LIC-LOCATION' with the olson name. - if (isset($vtimezone->{'X-LIC-LOCATION'})) { - - $lic = (string)$vtimezone->{'X-LIC-LOCATION'}; - - // Libical generators may specify strings like - // "SystemV/EST5EDT". For those we must remove the - // SystemV part. - if (substr($lic,0,8)==='SystemV/') { - $lic = substr($lic,8); - } - - try { - return new \DateTimeZone($lic); - } catch (\Exception $e) { - } - - } - // Microsoft may add a magic number, which we also have an - // answer for. - if (isset($vtimezone->{'X-MICROSOFT-CDO-TZID'})) { - $cdoId = (int)$vtimezone->{'X-MICROSOFT-CDO-TZID'}->value; - - // 2 can mean both Europe/Lisbon and Europe/Sarajevo. - if ($cdoId===2 && strpos((string)$vtimezone->TZID, 'Sarajevo')!==false) { - return new \DateTimeZone('Europe/Sarajevo'); - } - - if (isset(self::$microsoftExchangeMap[$cdoId])) { - return new \DateTimeZone(self::$microsoftExchangeMap[$cdoId]); - } - } - - } - - } - - } - - if ($failIfUncertain) { - throw new \InvalidArgumentException('We were unable to determine the correct PHP timezone for tzid: ' . $tzid); - } - - // If we got all the way here, we default to UTC. - return new \DateTimeZone(date_default_timezone_get()); - - } - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/Version.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,24 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * This class contains the version number for the VObject package - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class Version { - - /** - * Full version number - */ - const VERSION = '2.1.3'; - - /** - * Stability : alpha, beta, stable - */ - const STABILITY = 'stable'; - -}
--- a/plugins/libcalendaring/lib/Sabre/VObject/includes.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,41 +0,0 @@ -<?php - -/** - * Includes file - * - * This file includes the entire VObject library in one go. - * The benefit is that an autoloader is not needed, which is often faster. - * - * @copyright Copyright (C) 2007-2013 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ - -// Begin includes -include __DIR__ . '/DateTimeParser.php'; -include __DIR__ . '/ElementList.php'; -include __DIR__ . '/FreeBusyGenerator.php'; -include __DIR__ . '/Node.php'; -include __DIR__ . '/Parameter.php'; -include __DIR__ . '/ParseException.php'; -include __DIR__ . '/Property.php'; -include __DIR__ . '/Reader.php'; -include __DIR__ . '/RecurrenceIterator.php'; -include __DIR__ . '/Splitter/SplitterInterface.php'; -include __DIR__ . '/StringUtil.php'; -include __DIR__ . '/TimeZoneUtil.php'; -include __DIR__ . '/Version.php'; -include __DIR__ . '/Splitter/VCard.php'; -include __DIR__ . '/Component.php'; -include __DIR__ . '/Document.php'; -include __DIR__ . '/Property/Compound.php'; -include __DIR__ . '/Property/DateTime.php'; -include __DIR__ . '/Property/MultiDateTime.php'; -include __DIR__ . '/Splitter/ICalendar.php'; -include __DIR__ . '/Component/VAlarm.php'; -include __DIR__ . '/Component/VCalendar.php'; -include __DIR__ . '/Component/VEvent.php'; -include __DIR__ . '/Component/VFreeBusy.php'; -include __DIR__ . '/Component/VJournal.php'; -include __DIR__ . '/Component/VTodo.php'; -// End includes
--- a/vendor/autoload.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,7 +0,0 @@ -<?php - -// autoload.php @generated by Composer - -require_once __DIR__ . '/composer/autoload_real.php'; - -return ComposerAutoloaderInitd52cd7aa2b1301e6e89413f57235d2fc::getLoader();
--- a/vendor/sabre/vobject/.gitignore Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,18 +0,0 @@ -# Composer stuff -vendor/ -composer.lock -tests/cov/ -tests/temp - -#vim -.*.swp - -#binaries -bin/phpunit -bin/phpcs - -# Development stuff -testdata/ - -# OS X -.DS_Store
--- a/vendor/sabre/vobject/.travis.yml Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,17 +0,0 @@ -language: php -php: - - 5.3 - - 5.4 - - 5.5 - - 5.6 - - hhvm - -matrix: - fast_finish: true - -script: - - phpunit --configuration tests/phpunit.xml - - ./bin/phpcs -p --standard=tests/phpcs/ruleset.xml lib/ - - -before_script: composer install
--- a/vendor/sabre/vobject/ChangeLog.md Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,494 +0,0 @@ -ChangeLog -========= - -3.3.5 (2015-01-09) ------------------- - -* #168: Expanding calendars now removes objects with recurrence rules that - don't have a valid recurrence instance. -* #177: SCHEDULE-STATUS should not contain a reason phrase, only a status - code. -* #175: Parser can now read and skip the UTF-8 BOM. -* #179: Added `isFloating` to `DATE-TIME` properties. -* #179: Fixed jCal serialization of floating `DATE-TIME` properties. -* #173: vCard converter failed for `X-ABDATE` properties that had no - `X-ABLABEL`. - - -3.3.4 (2014-11-19) ------------------- - -* #154: Converting `ANNIVERSARY` to `X-ANNIVERSARY` and `X-ABDATE` and - vice-versa when converting to/from vCard 4. -* #154: It's now possible to easily select all vCard properties belonging to - a single group with `$vcard->{'ITEM1.'}` syntax. (@armin-hackmann) -* #156: Simpler way to check if a string is UTF-8. (@Hywan) -* Unittest improvements. -* #159: The recurrence iterator, freebusy generator and iCalendar DATE and - DATE-TIME properties can now all accept a reference timezone when working - floating times or all-day events. -* #159: Master events will no longer get a `RECURRENCE-ID` when expanding. -* #159: `RECURRENCE-ID` for all-day events will now be correct when expanding. -* #163: Added a `getTimeZone()` method to `VTIMEZONE` components. - - -3.3.3 (2014-10-09) ------------------- - -* #142: `CANCEL` and `REPLY` messages now include the `DTSTART` from the - original event. -* #143: `SCHEDULE-AGENT` on the `ORGANIZER` property is respected. -* #144: `PARTSTAT=NEEDS-ACTION` is now set for new invites, if no `PARTSTAT` is - set to support the inbox feature of iOS. -* #147: Bugs related to scheduling all-day events. -* #148: Ignore events that have attendees but no organizer. -* #149: Avoiding logging errors during timezone detection. This is a workaround - for a PHP bug. -* Support for "Line Islands Standard Time" windows timezone. -* #154: Correctly work around vCard parameters that have a value but no name. - - -3.3.2 (2014-09-19) ------------------- - -* Changed: iTip broker now sets RSVP status to false when replies are received. -* #118: iTip Message now has a `getScheduleStatus()` method. -* #119: Support for detecting 'significant changes'. -* #120: Support for `SCHEDULE-FORCE-SEND`. -* #121: iCal demands parameters containing the + sign to be quoted. -* #122: Don't generate REPLY messages for events that have been cancelled. -* #123: Added `SUMMARY` to iTip messages. -* #130: Incorrect validation rules for `RELATED` (should be `RELATED-TO`). -* #128: `ATTACH` in iCalendar is `URI` by default, not `BINARY`. -* #131: RRULE that doesn't provide a single valid instance now throws an - exception. -* #136: Validator rejects *all* control characters. We were missing a few. -* #133: Splitter objects will throw exceptions when receiving incompatible - objects. -* #127: Attendees who delete recurring event instances events they had already - declined earlier will no longer generate another reply. -* #125: Send CANCEL messages when ORGANIZER property gets deleted. - - -3.3.1 (2014-08-18) ------------------- - -* Changed: It's now possible to pass DateTime objects when using the magic - setters on properties. (`$event->DTSTART = new DateTime('now')`). -* #111: iTip Broker does not process attendee adding events to EXDATE. -* #112: EventIterator now sets TZID on RECURRENCE-ID. -* #113: Timezone support during creation of iTip REPLY messages. -* #114: VTIMEZONE is retained when generating new REQUEST objects. -* #114: Support for 'MAILTO:' style email addresses (in uppercase) in the iTip - broker. This improves evolution support. -* #115: Using REQUEST-STATUS from REPLY messages and now propegating that into - SCHEDULE-STATUS. - - -3.3.0 (2014-08-07) ------------------- - -* We now use PSR-4 for the directory structure. This means that everything - that was used to be in the `lib/Sabre/VObject` directory is now moved to - `lib/`. If you use composer to load this library, you shouldn't have to do - anything about that though. -* VEVENT now get populated with a DTSTAMP and UID property by default. -* BC Break: Removed the 'includes.php' file. Use composer instead. -* #103: Added support for processing [iTip][iTip] messages. This allows a user - to parse incoming iTip messages and apply the result on existing calendars, - or automatically generate invites/replies/cancellations based on changes that - a user made on objects. -* #75, #58, #18: Fixes related to overriding the first event in recurrences. -* Added: VCalendar::getBaseComponent to find the 'master' component in a - calendar. -* #51: Support for iterating RDATE properties. -* Fixed: Issue #101: RecurrenceIterator::nextMonthly() shows events that are - excluded events with wrong time - - -3.2.4 (2014-07-14) ------------------- - -* Added: Issue #98. The VCardConverter now takes `X-APPLE-OMIT-YEAR` into - consideration when converting between vCard 3 and 4. -* Fixed: Issue #96. Some support for Yahoo's broken vcards. -* Fixed: PHP 5.3 support was broken in the cli tool. - - -3.2.3 (2014-06-12) ------------------- - -* Validator now checks if DUE and DTSTART are of the same type in VTODO, and - ensures that DUE is always after DTSTART. -* Removed documentation from source repository, to http://sabre.io/vobject/ -* Expanded the vobject cli tool validation output to make it easier to find - issues. -* Fixed: vobject repair. It was not working for iCalendar objects. - - -3.2.2 (2014-05-07) ------------------- - -* Minor tweak in unittests to make it run on PHP 5.5.12. Json-prettifying - slightly changed which caused the test to fail. - - -3.2.1 (2014-05-03) ------------------- - -* Minor tweak to make the unittests run with the latest hhvm on travis. -* Updated timezone definitions. -* Updated copyright links to point to http://sabre.io/ - - -3.2.0 (2014-04-02) ------------------- - -* Now hhvm compatible! -* The validator can now detect a _lot_ more problems. Many rules for both - iCalendar and vCard were added. -* Added: bin/generate_vcards, a utility to generate random vcards for testing - purposes. Patches are welcome to add more data. -* Updated: Windows timezone mapping to latest version from unicode.org -* Changed: The timezone maps are now loaded in from external files, in - lib/Sabre/VObject/timezonedata. -* Added: Fixing badly encoded URL's from google contacts vcards. -* Fixed: Issue #68. Couldn't decode properties ending in a colon. -* Fixed: Issue #72. RecurrenceIterator should respect timezone in the UNTIL - clause. -* Fixed: Issue #67. BYMONTH limit on DAILY recurrences. -* Fixed: Issue #26. Return a more descriptive error when coming across broken - BYDAY rules. -* Fixed: Issue #28. Incorrect timezone detection for some timezones. -* Fixed: Issue #70. Casting a parameter with a null value to string would fail. -* Added: Support for rfc6715 and rfc6474. -* Added: Support for DateTime objects in the VCard DATE-AND-OR-TIME property. -* Added: UUIDUtil, for easily creating unique identifiers. -* Fixed: Issue #83. Creating new VALUE=DATE objects using php's DateTime. -* Fixed: Issue #86. Don't go into an infinite loop when php errors are - disabled and an invalid file is read. - - -3.1.4 (2014-03-30) ------------------- - -* Fixed: Issue #87: Several compatibility fixes related to timezone handling - changes in PHP 5.5.10. - - -3.1.3 (2013-10-02) ------------------- - -* Fixed: Support from properties from draft-daboo-valarm-extensions-04. Issue - #56. -* Fixed: Issue #54. Parsing a stream of multiple vcards separated by more than - one newline. Thanks @Vedmak for the patch. -* Fixed: Serializing vcard 2.1 parameters with no name caused a literal '1' to - be inserted. -* Added: VCardConverter removed properties that are no longer supported in vCard - 4.0. -* Added: vCards with a minimum number of values (such as N), but don't have that - many, are now automatically padded with empty components. -* Added: The vCard validator now also checks for a minimum number of components, - and has the ability to repair these. -* Added: Some support for vCard 2.1 in the VCard converter, to upgrade to vCard - 3.0 or 4.0. -* Fixed: Issue 60 Use Document::$componentMap when instantiating the top-level - VCalendar and VCard components. -* Fixed: Issue 62: Parsing iCalendar parameters with no value. -* Added: --forgiving option to vobject utility. -* Fixed: Compound properties such as ADR were not correctly split up in vCard - 2.1 quoted printable-encoded properties. -* Fixed: Issue 64: Encoding of binary properties of converted vCards. Thanks - @DominikTo for the patch. - - -3.1.2 (2013-08-13) ------------------- - -* Fixed: Setting correct property group on VCard conversion - - -3.1.1 (2013-08-02) ------------------- - -* Fixed: Issue #53. A regression in RecurrenceIterator. - - -3.1.0 (2013-07-27) ------------------- - -* Added: bad-ass new cli debugging utility (in bin/vobject). -* Added: jCal and jCard parser. -* Fixed: URI properties should not escape ; and ,. -* Fixed: VCard 4 documents now correctly use URI as a default value-type for - PHOTO and others. BINARY no longer exists in vCard 4. -* Added: Utility to convert between 2.1, 3.0 and 4.0 vCards. -* Added: You can now add() multiple parameters to a property in one call. -* Added: Parameter::has() for easily checking if a parameter value exists. -* Added: VCard::preferred() to find a preferred email, phone number, etc for a - contact. -* Changed: All $duration properties are now public. -* Added: A few validators for iCalendar documents. -* Fixed: Issue #50. RecurrenceIterator gives incorrect result when exception - events are out of order in the iCalendar file. -* Fixed: Issue #48. Overridden events in the recurrence iterator that were past - the UNTIL date were ignored. -* Added: getDuration for DURATION values such as TRIGGER. Thanks to - @SimonSimCity. -* Fixed: Issue #52. vCard 2.1 parameters with no name may lose values if there's - more than 1. Thanks to @Vedmak. - - -3.0.0 (2013-06-21) ------------------- - -* Fixed: includes.php file was still broken. Our tool to generate it had some - bugs. - - -3.0.0-beta4 (2013-06-21) ------------------------- - -* Fixed: includes.php was no longer up to date. - - -3.0.0-beta3 (2013-06-17) ------------------------- - -* Added: OPTION_FORGIVING now also allows slashes in property names. -* Fixed: DateTimeParser no longer fails on dates with years < 1000 & > 4999 -* Fixed: Issue 36: Workaround for the recurrenceiterator and caldav events with - a missing base event. -* Fixed: jCard encoding of TIME properties. -* Fixed: jCal encoding of REQUEST-STATUS, GEO and PERIOD values. - - -3.0.0-beta2 (2013-06-10) ------------------------- - -* Fixed: Corrected includes.php file. -* Fixed: vCard date-time parser supported extended-format dates as well. -* Changed: Properties have been moved to an ICalendar or VCard directory. -* Fixed: Couldn't parse vCard 3 extended format dates and times. -* Fixed: Couldn't export jCard DATE values correctly. -* Fixed: Recursive loop in ICalendar\DateTime property. - - -3.0.0-beta1 (2013-06-07) ------------------------- - -* Added: jsonSerialize() for creating jCal and jCard documents. -* Added: helper method to parse vCard dates and times. -* Added: Specialized classes for FLOAT, LANGUAGE-TAG, TIME, TIMESTAMP, - DATE-AND-OR-TIME, CAL-ADDRESS, UNKNOWN and UTC-OFFSET properties. -* Removed: CommaSeparatedText property. Now included into Text. -* Fixed: Multiple parameters with the same name are now correctly encoded. -* Fixed: Parameter values containing a comma are now enclosed in double-quotes. -* Fixed: Iterating parameter values should now fully work as expected. -* Fixed: Support for vCard 2.1 nameless parameters. -* Changed: $valueMap, $componentMap and $propertyMap now all use fully-qualified - class names, so they are actually overridable. -* Fixed: Updating DATE-TIME to DATE values now behaves like expected. - - -3.0.0-alpha4 (2013-05-31) -------------------------- - -* Added: It's now possible to send parser options to the splitter classes. -* Added: A few tweaks to improve component and property creation. - - -3.0.0-alpha3 (2013-05-13) -------------------------- - -* Changed: propertyMap, valueMap and componentMap are now static properties. -* Changed: Component::remove() will throw an exception when trying to a node - that's not a child of said component. -* Added: Splitter objects are now faster, line numbers are accurately reported - and use less memory. -* Added: MimeDir parser can now continue parsing with the same stream buffer. -* Fixed: vobjectvalidate.php is operational again. -* Fixed: \r is properly stripped in text values. -* Fixed: QUOTED-PRINTABLE is now correctly encoded as well as encoded, for - vCards 2.1. -* Fixed: Parser assumes vCard 2.1, if no version was supplied. - - -3.0.0-alpha2 (2013-05-22) -------------------------- - -* Fixed: vCard URL properties were referencing a non-existant class. - - -3.0.0-alpha1 (2013-05-21) -------------------------- - -* Fixed: Now correctly dealing with escaping of properties. This solves the - problem with double-backslashes where they don't belong. -* Added: Easy support for properties with more than one value, using setParts - and getParts. -* Added: Support for broken 2.1 vCards produced by microsoft. -* Added: Automatically decoding quoted-printable values. -* Added: Automatically decoding base64 values. -* Added: Decoding RFC6868 parameter values (uses ^ as an escape character). -* Added: Fancy new MimeDir parser that can also parse streams. -* Added: Automatically mapping many, many properties to a property-class with - specialized API's. -* Added: remove() method for easily removing properties and sub-components - components. -* Changed: Components, Properties and Parameters can no longer be created with - Component::create, Property::create and Parameter::create. They must instead - be created through the root component. (A VCalendar or VCard object). -* Changed: API for DateTime properties has slightly changed. -* Changed: the ->value property is now protected everywhere. Use getParts() and - getValue() instead. -* BC Break: No support for mac newlines (\r). Never came across these anyway. -* Added: add() method to the Property class. -* Added: It's now possible to easy set multi-value properties as arrays. -* Added: When setting date-time properties you can just pass PHP's DateTime - object. -* Added: New components automatically get a bunch of default properties, such as - VERSION and CALSCALE. -* Added: You can add new sub-components much quicker with the magic setters, and - add() method. - - -2.1.6 (2014-12-10) ------------------- - -* Fixed: Minor change to make sure that unittests succeed on every PHP version. - - -2.1.5 (2014-06-03) ------------------- - -* Fixed: #94: Better parameter escaping. -* Changed: Documentation cleanups. - - -2.1.4 (2014-03-30) ------------------- - -* Fixed: Issue #87: Several compatibility fixes related to timezone handling - changes in PHP 5.5.10. - - -2.1.3 (2013-10-02) ------------------- - -* Fixed: Issue #55. \r must be stripped from property values. -* Fixed: Issue #65. Putting quotes around parameter values that contain a colon. - - -2.1.2 (2013-08-02) ------------------- - -* Fixed: Issue #53. A regression in RecurrenceIterator. - - -2.1.1 (2013-07-27) ------------------- - -* Fixed: Issue #50. RecurrenceIterator gives incorrect result when exception - events are out of order in the iCalendar file. -* Fixed: Issue #48. Overridden events in the recurrence iterator that were past - the UNTIL date were ignored. - - -2.1.0 (2013-06-17) ------------------- - -* This version is fully backwards compatible with 2.0.\*. However, it contains a - few new API's that mimic the VObject 3 API. This allows it to be used a - 'bridge' version. Specifically, this new version exists so SabreDAV 1.7 and - 1.8 can run with both the 2 and 3 versions of this library. -* Added: Property\DateTime::hasTime(). -* Added: Property\MultiDateTime::hasTime(). -* Added: Property::getValue(). -* Added: Document class. -* Added: Document::createComponent and Document::createProperty. -* Added: Parameter::getValue(). - - -2.0.7 (2013-03-05) ------------------- - -* Fixed: Microsoft re-uses their magic numbers for different timezones, - specifically id 2 for both Sarajevo and Lisbon). A workaround was added to - deal with this. - - -2.0.6 (2013-02-17) ------------------- - -* Fixed: The reader now properly parses parameters without a value. - - -2.0.5 (2012-11-05) ------------------- - -* Fixed: The FreeBusyGenerator is now properly using the factory methods for - creation of components and properties. - - -2.0.4 (2012-11-02) ------------------- - -* Added: Known Lotus Notes / Domino timezone id's. - - -2.0.3 (2012-10-29) ------------------- - -* Added: Support for 'GMT+????' format in TZID's. -* Added: Support for formats like SystemV/EST5EDT in TZID's. -* Fixed: RecurrenceIterator now repairs recurrence rules where UNTIL < DTSTART. -* Added: Support for BYHOUR in FREQ=DAILY (@hollodk). -* Added: Support for BYHOUR and BYDAY in FREQ=WEEKLY. - - -2.0.2 (2012-10-06) ------------------- - -* Added: includes.php file, to load the entire library in one go. -* Fixed: A problem with determining alarm triggers for TODO's. - - -2.0.1 (2012-09-22) ------------------- - -* Removed: Element class. It wasn't used. -* Added: Basic validation and repair methods for broken input data. -* Fixed: RecurrenceIterator could infinitely loop when an INTERVAL of 0 was - specified. -* Added: A cli script that can validate and automatically repair vcards and - iCalendar objects. -* Added: A new 'Compound' property, that can automatically split up parts for - properties such as N, ADR, ORG and CATEGORIES. -* Added: Splitter classes, that can split up large objects (such as exports) - into individual objects (thanks @DominikTO and @armin-hackmann). -* Added: VFREEBUSY component, which allows easily checking wether timeslots are - available. -* Added: The Reader class now has a 'FORGIVING' option, which allows it to parse - properties with incorrect characters in the name (at this time, it just allows - underscores). -* Added: Also added the 'IGNORE_INVALID_LINES' option, to completely disregard - any invalid lines. -* Fixed: A bug in Windows timezone-id mappings for times created in Greenlands - timezone (sorry Greenlanders! I do care!). -* Fixed: DTEND was not generated correctly for VFREEBUSY reports. -* Fixed: Parser is at least 25% faster with real-world data. - - -2.0.0 (2012-08-08) ------------------- - -* VObject is now a separate project from SabreDAV. See the SabreDAV changelog - for version information before 2.0. -* New: VObject library now uses PHP 5.3 namespaces. -* New: It's possible to specify lists of parameters when constructing - properties. -* New: made it easier to construct the FreeBusyGenerator. - -[iTip]: http://tools.ietf.org/html/rfc5546
--- a/vendor/sabre/vobject/LICENSE Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,27 +0,0 @@ -Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/) - -All rights reserved. - -Redistribution and use in source and binary forms, with or without modification, -are permitted provided that the following conditions are met: - - * Redistributions of source code must retain the above copyright notice, - this list of conditions and the following disclaimer. - * Redistributions in binary form must reproduce the above copyright notice, - this list of conditions and the following disclaimer in the documentation - and/or other materials provided with the distribution. - * Neither the name Sabre nor the names of its contributors - may be used to endorse or promote products derived from this software - without specific prior written permission. - - THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" - AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE - LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - POSSIBILITY OF SUCH DAMAGE.
--- a/vendor/sabre/vobject/README.md Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,50 +0,0 @@ -sabre/vobject -============= - -The VObject library allows you to easily parse and manipulate [iCalendar](https://tools.ietf.org/html/rfc5545) -and [vCard](https://tools.ietf.org/html/rfc6350) objects using PHP. - -The goal of the VObject library is to create a very complete library, with an easy to use API. - -Build status ------------- - -| branch | status | -| ------ | ------ | -| master | [](https://travis-ci.org/fruux/sabre-vobject) | -| 3.3 | [](https://travis-ci.org/fruux/sabre-vobject) | -| 3.1 | [](https://travis-ci.org/fruux/sabre-vobject) | -| 2.1 | [](https://travis-ci.org/fruux/sabre-vobject) | -| 2.0 | [](https://travis-ci.org/fruux/sabre-vobject) | - - -Installation ------------- - -VObject requires PHP 5.3, and should be installed using composer. -The general composer instructions can be found on the [composer website](http://getcomposer.org/doc/00-intro.md composer website). - -After that, just declare the vobject dependency as follows: - - "require" : { - "sabre/vobject" : "~3.3" - } - -Then, run `composer.phar update` and you should be good. - -Usage ------ - -* [3.x documentation](http://sabre.io/vobject/usage/) -* [2.x documentation](http://sabre.io/vobject/usage_2/) -* [Migrating from 2.x to 3.x](http://sabre.io/vobject/upgrade/) - -Support -------- - -Head over to the [SabreDAV mailing list](http://groups.google.com/group/sabredav-discuss) for any questions. - -Made at fruux -------------- - -This library is being developed by [fruux](https://fruux.com/). Drop us a line for commercial services or enterprise support.
--- a/vendor/sabre/vobject/bin/bench.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,12 +0,0 @@ -#!/usr/bin/env php -<?php - -include __DIR__ . '/../vendor/autoload.php'; - -$data = stream_get_contents(STDIN); - -$start = microtime(true); - -$lol = Sabre\VObject\Reader::read($data); - -echo "time: " . (microtime(true)-$start) . "\n";
--- a/vendor/sabre/vobject/bin/fetch_windows_zones.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,47 +0,0 @@ -#!/usr/bin/env php -<?php - -$windowsZonesUrl = 'http://unicode.org/repos/cldr/trunk/common/supplemental/windowsZones.xml'; -$outputFile = __DIR__ . '/../lib/timezonedata/windowszones.php'; - -echo "Fetching timezone map from: " . $windowsZonesUrl, "\n"; - -$data = file_get_contents($windowsZonesUrl); - -$xml = simplexml_load_string($data); - -$map = []; - -foreach($xml->xpath('//mapZone') as $mapZone) { - - $from = (string)$mapZone['other']; - $to = (string)$mapZone['type']; - - list($to) = explode(' ', $to, 2); - - if (!isset($map[$from])) { - $map[$from] = $to; - } - -} - -ksort($map); -echo "Writing to: $outputFile\n"; - -$f = fopen($outputFile,'w'); -fwrite($f, "<?php\n\n"); -fwrite($f, "/**\n"); -fwrite($f, " * Automatically generated timezone file\n"); -fwrite($f, " *\n"); -fwrite($f, " * Last update: " . date(DATE_W3C) . "\n"); -fwrite($f, " * Source: " .$windowsZonesUrl . "\n"); -fwrite($f, " *\n"); -fwrite($f, " * @copyright Copyright (C) 2007-2014 fruux GmbH (https://fruux.com/).\n"); -fwrite($f, " * @license http://sabre.io/license/ Modified BSD License\n"); -fwrite($f, " */\n"); -fwrite($f, "\n"); -fwrite($f, "return "); -fwrite($f, var_export($map, true) . ';'); -fclose($f); - -echo "Done\n";
--- a/vendor/sabre/vobject/bin/generate_vcards Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,241 +0,0 @@ -#!/usr/bin/env php -<?php - -namespace Sabre\VObject; - -// This sucks.. we have to try to find the composer autoloader. But chances -// are, we can't find it this way. So we'll do our bestest -$paths = array( - __DIR__ . '/../vendor/autoload.php', // In case vobject is cloned directly - __DIR__ . '/../../../autoload.php', // In case vobject is a composer dependency. -); - -foreach($paths as $path) { - if (file_exists($path)) { - include $path; - break; - } -} - -if (!class_exists('Sabre\\VObject\\Version')) { - fwrite(STDERR, "Composer autoloader could not be properly loaded.\n"); - die(1); -} - -if ($argc < 2) { - - $version = Version::VERSION; - - $help = <<<HI -sabre/vobject $version -Usage: - generate_vcards [count] - -Options: - count The number of random vcards to generate - -Examples: - generate_vcards 1000 > testdata.vcf - -HI; - - fwrite(STDERR, $help); - exit(2); -} - -$count = (int)$argv[1]; -if ($count < 1) { - fwrite(STDERR, "Count must be at least 1\n"); - exit(2); -} - -fwrite(STDERR, "sabre/vobject " . Version::VERSION . "\n"); -fwrite(STDERR, "Generating " . $count . " vcards in vCard 4.0 format\n"); - -/** - * The following list is just some random data we compiled from various - * sources online. - * - * Very little thought went into compiling this list, and certainly nothing - * political or ethical. - * - * We would _love_ more additions to this to add more variation to this list. - * - * Send us PR's and don't be shy adding your own first and last name for fun. - */ - -$sets = [ - "nl" => [ - "country" => "Netherlands", - "boys" => [ - "Anno", - "Bram", - "Daan", - "Evert", - "Finn", - "Jayden", - "Jens", - "Jesse", - "Levi", - "Lucas", - "Luuk", - "Milan", - "René", - "Sem", - "Sibrand", - "Willem", - ], - "girls" => [ - "Celia", - "Emma", - "Fenna", - "Geke", - "Inge", - "Julia", - "Lisa", - "Lotte", - "Mila", - "Sara", - "Sophie", - "Tess", - "Zoë", - ], - "last" => [ - "Bakker", - "Bos", - "De Boer", - "De Groot", - "De Jong", - "De Vries", - "Jansen", - "Janssen", - "Meyer", - "Mulder", - "Peters", - "Smit", - "Van Dijk", - "Van den Berg", - "Visser", - "Vos", - ], - ], - "us" => [ - "country" => "United States", - "boys" => [ - "Aiden", - "Alexander", - "Charles", - "David", - "Ethan", - "Jacob", - "James", - "Jayden", - "John", - "Joseph", - "Liam", - "Mason", - "Michael", - "Noah", - "Richard", - "Robert", - "Thomas", - "William", - ], - "girls" => [ - "Ava", - "Barbara", - "Chloe", - "Dorothy", - "Elizabeth", - "Emily", - "Emma", - "Isabella", - "Jennifer", - "Lily", - "Linda", - "Margaret", - "Maria", - "Mary", - "Mia", - "Olivia", - "Patricia", - "Roxy", - "Sophia", - "Susan", - "Zoe", - ], - "last" => [ - "Smith", - "Johnson", - "Williams", - "Jones", - "Brown", - "Davis", - "Miller", - "Wilson", - "Moore", - "Taylor", - "Anderson", - "Thomas", - "Jackson", - "White", - "Harris", - "Martin", - "Thompson", - "Garcia", - "Martinez", - "Robinson", - ], - ], -]; - -$current = 0; - -$r = function($arr) { - - return $arr[mt_rand(0,count($arr)-1)]; - -}; - -$bdayStart = strtotime('-85 years'); -$bdayEnd = strtotime('-20 years'); - -while($current < $count) { - - $current++; - fwrite(STDERR, "\033[100D$current/$count"); - - $country = array_rand($sets); - $gender = mt_rand(0,1)?'girls':'boys'; - - $vcard = new Component\VCard([ - 'VERSION' => '4.0', - 'FN' => $r($sets[$country][$gender]) . ' ' . $r($sets[$country]['last']), - 'UID' => UUIDUtil::getUUID(), - ]); - - $bdayRatio = mt_rand(0,9); - - if($bdayRatio < 2) { - // 20% has a birthday property with a full date - $dt = new \DateTime('@' . mt_rand($bdayStart, $bdayEnd)); - $vcard->add('BDAY', $dt->format('Ymd')); - - } elseif ($bdayRatio < 3) { - // 10% we only know the month and date of - $dt = new \DateTime('@' . mt_rand($bdayStart, $bdayEnd)); - $vcard->add('BDAY', '--' . $dt->format('md')); - } - if ($result = $vcard->validate()) { - ob_start(); - echo "\nWe produced an invalid vcard somehow!\n"; - foreach($result as $message) { - echo " " . $message['message'] . "\n"; - } - fwrite(STDERR, ob_get_clean()); - } - echo $vcard->serialize(); - -} - -fwrite(STDERR,"\nDone.\n");
--- a/vendor/sabre/vobject/bin/generateicalendardata.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,91 +0,0 @@ -#!/usr/bin/env php -<?php - -use Sabre\VObject; - -if ($argc<2) { - $cmd = $argv[0]; - fwrite(STDERR, <<<HI -Fruux test data generator - -This script generates a lot of test data. This is used for profiling and stuff. -Currently it just generates events in a single calendar. - -The iCalendar output goes to stdout. Other messages to stderr. - -{$cmd} [events] - - -HI - ); - die(); -} - -$events = 100; - -if (isset($argv[1])) $events = (int)$argv[1]; - -include __DIR__ . '/../vendor/autoload.php'; - -fwrite(STDERR, "Generating " . $events . " events\n"); - -$currentDate = new DateTime('-' . round($events/2) . ' days'); - -$calendar = VObject\Component::create('VCALENDAR'); -$calendar->version = '2.0'; -$calendar->calscale = 'GREGORIAN'; - -$ii=0; - -while($ii < $events) { - - $ii++; - - $event = VObject\Component::create('VEVENT'); - $event->DTSTART = 'bla'; - $event->SUMMARY = 'Event #' . $ii; - $event->UID = md5(microtime(true)); - - $doctorRandom = mt_rand(1,1000); - - switch($doctorRandom) { - // All-day event - case 1 : - $event->DTEND = 'bla'; - $dtStart = clone $currentDate; - $dtEnd = clone $currentDate; - $dtEnd->modify('+' . mt_rand(1,3) . ' days'); - $event->DTSTART->setDateTime($dtStart, VObject\Property\DateTime::DATE); - $event->DTEND->setDateTime($dtEnd, VObject\Property\DateTime::DATE); - break; - case 2 : - $event->RRULE = 'FREQ=DAILY;COUNT=' . mt_rand(1,10); - // No break intentional - default : - $dtStart = clone $currentDate; - $dtStart->setTime(mt_rand(1,23), mt_rand(0,59), mt_rand(0,59)); - $event->DTSTART->setDateTime($dtStart, VObject\Property\DateTime::UTC); - $event->DURATION = 'PT'.mt_rand(1,3).'H'; - break; - - } - - $calendar->add($event); - $currentDate->modify('+ ' . mt_rand(0,3) . ' days'); - -} -fwrite(STDERR, "Validating\n"); - -$result = $calendar->validate(); -if ($result) { - fwrite(STDERR, "Errors!\n"); - fwrite(STDERR, print_r($result,true)); - die(-1); -} - -fwrite(STDERR, "Serializing this beast\n"); - -echo $calendar->serialize(); - -fwrite(STDERR, "done.\n"); -
--- a/vendor/sabre/vobject/bin/vobject Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,27 +0,0 @@ -#!/usr/bin/env php -<?php - -namespace Sabre\VObject; - -// This sucks.. we have to try to find the composer autoloader. But chances -// are, we can't find it this way. So we'll do our bestest -$paths = array( - __DIR__ . '/../vendor/autoload.php', // In case vobject is cloned directly - __DIR__ . '/../../../autoload.php', // In case vobject is a composer dependency. -); - -foreach($paths as $path) { - if (file_exists($path)) { - include $path; - break; - } -} - -if (!class_exists('Sabre\\VObject\\Version')) { - fwrite(STDERR, "Composer autoloader could not be loaded.\n"); - die(1); -} - -$cli = new Cli(); -exit($cli->main($argv)); -
--- a/vendor/sabre/vobject/composer.json Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,50 +0,0 @@ -{ - "name": "sabre/vobject", - "description" : "The VObject library for PHP allows you to easily parse and manipulate iCalendar and vCard objects", - "keywords" : [ "VObject", "iCalendar", "vCard", "jCard", "jCal" ], - "homepage" : "http://sabre.io/vobject/", - "license" : "BSD-3-Clause", - "require" : { - "php" : ">=5.3.1", - "ext-mbstring" : "*" - }, - "require-dev" : { - "phpunit/phpunit" : "*", - "squizlabs/php_codesniffer": "*" - }, - "authors" : [ - { - "name" : "Evert Pot", - "email" : "me@evertpot.com", - "homepage" : "http://evertpot.com/", - "role" : "Developer" - }, - { - "name" : "Dominik Tobschall", - "email" : "dominik@fruux.com", - "homepage" : "http://tobschall.de/", - "role" : "Developer" - } - ], - "support" : { - "forum" : "https://groups.google.com/group/sabredav-discuss", - "source" : "https://github.com/fruux/sabre-vobject" - }, - "autoload" : { - "psr-4" : { - "Sabre\\VObject\\" : "lib/" - } - }, - "bin" : [ - "bin/vobject", - "bin/generate_vcards" - ], - "extra" : { - "branch-alias" : { - "dev-master" : "3.2.x-dev" - } - }, - "config" : { - "bin-dir" : "bin" - } -}
--- a/vendor/sabre/vobject/lib/Cli.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,761 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - InvalidArgumentException; - -/** - * This is the CLI interface for sabre-vobject. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Cli { - - /** - * No output - * - * @var bool - */ - protected $quiet = false; - - /** - * Help display - * - * @var bool - */ - protected $showHelp = false; - - /** - * Wether to spit out 'mimedir' or 'json' format. - * - * @var string - */ - protected $format; - - /** - * JSON pretty print - * - * @var bool - */ - protected $pretty; - - /** - * Source file - * - * @var string - */ - protected $inputPath; - - /** - * Destination file - * - * @var string - */ - protected $outputPath; - - /** - * output stream - * - * @var resource - */ - protected $stdout; - - /** - * stdin - * - * @var resource - */ - protected $stdin; - - /** - * stderr - * - * @var resource - */ - protected $stderr; - - /** - * Input format (one of json or mimedir) - * - * @var string - */ - protected $inputFormat; - - /** - * Makes the parser less strict. - * - * @var bool - */ - protected $forgiving = false; - - /** - * Main function - * - * @return int - */ - public function main(array $argv) { - - // @codeCoverageIgnoreStart - // We cannot easily test this, so we'll skip it. Pretty basic anyway. - - if (!$this->stderr) { - $this->stderr = fopen('php://stderr', 'w'); - } - if (!$this->stdout) { - $this->stdout = fopen('php://stdout', 'w'); - } - if (!$this->stdin) { - $this->stdin = fopen('php://stdin', 'r'); - } - - // @codeCoverageIgnoreEnd - - - try { - - list($options, $positional) = $this->parseArguments($argv); - - if (isset($options['q'])) { - $this->quiet = true; - } - $this->log($this->colorize('green', "sabre/vobject ") . $this->colorize('yellow', Version::VERSION)); - - foreach($options as $name=>$value) { - - switch($name) { - - case 'q' : - // Already handled earlier. - break; - case 'h' : - case 'help' : - $this->showHelp(); - return 0; - break; - case 'format' : - switch($value) { - - // jcard/jcal documents - case 'jcard' : - case 'jcal' : - - // specific document versions - case 'vcard21' : - case 'vcard30' : - case 'vcard40' : - case 'icalendar20' : - - // specific formats - case 'json' : - case 'mimedir' : - - // icalendar/vcad - case 'icalendar' : - case 'vcard' : - $this->format = $value; - break; - - default : - throw new InvalidArgumentException('Unknown format: ' . $value); - - } - break; - case 'pretty' : - if (version_compare(PHP_VERSION, '5.4.0') >= 0) { - $this->pretty = true; - } - break; - case 'forgiving' : - $this->forgiving = true; - break; - case 'inputformat' : - switch($value) { - // json formats - case 'jcard' : - case 'jcal' : - case 'json' : - $this->inputFormat = 'json'; - break; - - // mimedir formats - case 'mimedir' : - case 'icalendar' : - case 'vcard' : - case 'vcard21' : - case 'vcard30' : - case 'vcard40' : - case 'icalendar20' : - - $this->inputFormat = 'mimedir'; - break; - - default : - throw new InvalidArgumentException('Unknown format: ' . $value); - - } - break; - default : - throw new InvalidArgumentException('Unknown option: ' . $name); - - } - - } - - if (count($positional) === 0) { - $this->showHelp(); - return 1; - } - - if (count($positional) === 1) { - throw new InvalidArgumentException('Inputfile is a required argument'); - } - - if (count($positional) > 3) { - throw new InvalidArgumentException('Too many arguments'); - } - - if (!in_array($positional[0], array('validate','repair','convert','color'))) { - throw new InvalidArgumentException('Uknown command: ' . $positional[0]); - } - - } catch (InvalidArgumentException $e) { - $this->showHelp(); - $this->log('Error: ' . $e->getMessage(), 'red'); - return 1; - } - - $command = $positional[0]; - - $this->inputPath = $positional[1]; - $this->outputPath = isset($positional[2])?$positional[2]:'-'; - - if ($this->outputPath !== '-') { - $this->stdout = fopen($this->outputPath, 'w'); - } - - if (!$this->inputFormat) { - if (substr($this->inputPath, -5)==='.json') { - $this->inputFormat = 'json'; - } else { - $this->inputFormat = 'mimedir'; - } - } - if (!$this->format) { - if (substr($this->outputPath,-5)==='.json') { - $this->format = 'json'; - } else { - $this->format = 'mimedir'; - } - } - - - $realCode = 0; - - try { - - while($input = $this->readInput()) { - - $returnCode = $this->$command($input); - if ($returnCode!==0) $realCode = $returnCode; - - } - - } catch (EofException $e) { - // end of file - } catch (\Exception $e) { - $this->log('Error: ' . $e->getMessage(),'red'); - return 2; - } - - return $realCode; - - } - - /** - * Shows the help message. - * - * @return void - */ - protected function showHelp() { - - $this->log('Usage:', 'yellow'); - $this->log(" vobject [options] command [arguments]"); - $this->log(''); - $this->log('Options:', 'yellow'); - $this->log($this->colorize('green', ' -q ') . "Don't output anything."); - $this->log($this->colorize('green', ' -help -h ') . "Display this help message."); - $this->log($this->colorize('green', ' --format ') . "Convert to a specific format. Must be one of: vcard, vcard21,"); - $this->log($this->colorize('green', ' --forgiving ') . "Makes the parser less strict."); - $this->log(" vcard30, vcard40, icalendar20, jcal, jcard, json, mimedir."); - $this->log($this->colorize('green', ' --inputformat ') . "If the input format cannot be guessed from the extension, it"); - $this->log(" must be specified here."); - // Only PHP 5.4 and up - if (version_compare(PHP_VERSION, '5.4.0') >= 0) { - $this->log($this->colorize('green', ' --pretty ') . "json pretty-print."); - } - $this->log(''); - $this->log('Commands:', 'yellow'); - $this->log($this->colorize('green', ' validate') . ' source_file Validates a file for correctness.'); - $this->log($this->colorize('green', ' repair') . ' source_file [output_file] Repairs a file.'); - $this->log($this->colorize('green', ' convert') . ' source_file [output_file] Converts a file.'); - $this->log($this->colorize('green', ' color') . ' source_file Colorize a file, useful for debbugging.'); - $this->log( - <<<HELP - -If source_file is set as '-', STDIN will be used. -If output_file is omitted, STDOUT will be used. -All other output is sent to STDERR. - -HELP - ); - - $this->log('Examples:', 'yellow'); - $this->log(' vobject convert contact.vcf contact.json'); - $this->log(' vobject convert --format=vcard40 old.vcf new.vcf'); - $this->log(' vobject convert --inputformat=json --format=mimedir - -'); - $this->log(' vobject color calendar.ics'); - $this->log(''); - $this->log('https://github.com/fruux/sabre-vobject','purple'); - - } - - /** - * Validates a VObject file - * - * @param Component $vObj - * @return int - */ - protected function validate($vObj) { - - $returnCode = 0; - - switch($vObj->name) { - case 'VCALENDAR' : - $this->log("iCalendar: " . (string)$vObj->VERSION); - break; - case 'VCARD' : - $this->log("vCard: " . (string)$vObj->VERSION); - break; - } - - $warnings = $vObj->validate(); - if (!count($warnings)) { - $this->log(" No warnings!"); - } else { - - $levels = array( - 1 => 'REPAIRED', - 2 => 'WARNING', - 3 => 'ERROR', - ); - $returnCode = 2; - foreach($warnings as $warn) { - - $extra = ''; - if ($warn['node'] instanceof Property) { - $extra = ' (property: "' . $warn['node']->name . '")'; - } - $this->log(" [" . $levels[$warn['level']] . '] ' . $warn['message'] . $extra); - - } - - } - - return $returnCode; - - } - - /** - * Repairs a VObject file - * - * @param Component $vObj - * @return int - */ - protected function repair($vObj) { - - $returnCode = 0; - - switch($vObj->name) { - case 'VCALENDAR' : - $this->log("iCalendar: " . (string)$vObj->VERSION); - break; - case 'VCARD' : - $this->log("vCard: " . (string)$vObj->VERSION); - break; - } - - $warnings = $vObj->validate(Node::REPAIR); - if (!count($warnings)) { - $this->log(" No warnings!"); - } else { - - $levels = array( - 1 => 'REPAIRED', - 2 => 'WARNING', - 3 => 'ERROR', - ); - $returnCode = 2; - foreach($warnings as $warn) { - - $extra = ''; - if ($warn['node'] instanceof Property) { - $extra = ' (property: "' . $warn['node']->name . '")'; - } - $this->log(" [" . $levels[$warn['level']] . '] ' . $warn['message'] . $extra); - - } - - } - fwrite($this->stdout, $vObj->serialize()); - - return $returnCode; - - } - - /** - * Converts a vObject file to a new format. - * - * @param Component $vObj - * @return int - */ - protected function convert($vObj) { - - $json = false; - $convertVersion = null; - $forceInput = null; - - switch($this->format) { - case 'json' : - $json = true; - if ($vObj->name === 'VCARD') { - $convertVersion = Document::VCARD40; - } - break; - case 'jcard' : - $json = true; - $forceInput = 'VCARD'; - $convertVersion = Document::VCARD40; - break; - case 'jcal' : - $json = true; - $forceInput = 'VCALENDAR'; - break; - case 'mimedir' : - case 'icalendar' : - case 'icalendar20' : - case 'vcard' : - break; - case 'vcard21' : - $convertVersion = Document::VCARD21; - break; - case 'vcard30' : - $convertVersion = Document::VCARD30; - break; - case 'vcard40' : - $convertVersion = Document::VCARD40; - break; - - } - - if ($forceInput && $vObj->name !== $forceInput) { - throw new \Exception('You cannot convert a ' . strtolower($vObj->name) . ' to ' . $this->format); - } - if ($convertVersion) { - $vObj = $vObj->convert($convertVersion); - } - if ($json) { - $jsonOptions = 0; - if ($this->pretty) { - $jsonOptions = JSON_PRETTY_PRINT; - } - fwrite($this->stdout, json_encode($vObj->jsonSerialize(), $jsonOptions)); - } else { - fwrite($this->stdout, $vObj->serialize()); - } - - return 0; - - } - - /** - * Colorizes a file - * - * @param Component $vObj - * @return int - */ - protected function color($vObj) { - - fwrite($this->stdout, $this->serializeComponent($vObj)); - - } - - /** - * Returns an ansi color string for a color name. - * - * @param string $color - * @return string - */ - protected function colorize($color, $str, $resetTo = 'default') { - - $colors = array( - 'cyan' => '1;36', - 'red' => '1;31', - 'yellow' => '1;33', - 'blue' => '0;34', - 'green' => '0;32', - 'default' => '0', - 'purple' => '0;35', - ); - return "\033[" . $colors[$color] . 'm' . $str . "\033[".$colors[$resetTo]."m"; - - } - - /** - * Writes out a string in specific color. - * - * @param string $color - * @param string $str - * @return void - */ - protected function cWrite($color, $str) { - - fwrite($this->stdout, $this->colorize($color, $str)); - - } - - protected function serializeComponent(Component $vObj) { - - $this->cWrite('cyan', 'BEGIN'); - $this->cWrite('red', ':'); - $this->cWrite('yellow', $vObj->name . "\n"); - - /** - * Gives a component a 'score' for sorting purposes. - * - * This is solely used by the childrenSort method. - * - * A higher score means the item will be lower in the list. - * To avoid score collisions, each "score category" has a reasonable - * space to accomodate elements. The $key is added to the $score to - * preserve the original relative order of elements. - * - * @param int $key - * @param array $array - * @return int - */ - $sortScore = function($key, $array) { - - if ($array[$key] instanceof Component) { - - // We want to encode VTIMEZONE first, this is a personal - // preference. - if ($array[$key]->name === 'VTIMEZONE') { - $score=300000000; - return $score+$key; - } else { - $score=400000000; - return $score+$key; - } - } else { - // Properties get encoded first - // VCARD version 4.0 wants the VERSION property to appear first - if ($array[$key] instanceof Property) { - if ($array[$key]->name === 'VERSION') { - $score=100000000; - return $score+$key; - } else { - // All other properties - $score=200000000; - return $score+$key; - } - } - } - - }; - - $tmp = $vObj->children; - uksort( - $vObj->children, - function($a, $b) use ($sortScore, $tmp) { - - $sA = $sortScore($a, $tmp); - $sB = $sortScore($b, $tmp); - - return $sA - $sB; - - } - ); - - foreach($vObj->children as $child) { - if ($child instanceof Component) { - $this->serializeComponent($child); - } else { - $this->serializeProperty($child); - } - } - - $this->cWrite('cyan', 'END'); - $this->cWrite('red', ':'); - $this->cWrite('yellow', $vObj->name . "\n"); - - } - - /** - * Colorizes a property. - * - * @param Property $property - * @return void - */ - protected function serializeProperty(Property $property) { - - if ($property->group) { - $this->cWrite('default', $property->group); - $this->cWrite('red', '.'); - } - - $str = ''; - $this->cWrite('yellow', $property->name); - - foreach($property->parameters as $param) { - - $this->cWrite('red',';'); - $this->cWrite('blue', $param->serialize()); - - } - $this->cWrite('red',':'); - - if ($property instanceof Property\Binary) { - - $this->cWrite('default', 'embedded binary stripped. (' . strlen($property->getValue()) . ' bytes)'); - - } else { - - $parts = $property->getParts(); - $first1 = true; - // Looping through property values - foreach($parts as $part) { - if ($first1) { - $first1 = false; - } else { - $this->cWrite('red', $property->delimiter); - } - $first2 = true; - // Looping through property sub-values - foreach((array)$part as $subPart) { - if ($first2) { - $first2 = false; - } else { - // The sub-value delimiter is always comma - $this->cWrite('red', ','); - } - - $subPart = strtr( - $subPart, - array( - '\\' => $this->colorize('purple', '\\\\', 'green'), - ';' => $this->colorize('purple', '\;', 'green'), - ',' => $this->colorize('purple', '\,', 'green'), - "\n" => $this->colorize('purple', "\\n\n\t", 'green'), - "\r" => "", - ) - ); - - $this->cWrite('green', $subPart); - } - } - - } - $this->cWrite("default", "\n"); - - } - - /** - * Parses the list of arguments. - * - * @param array $argv - * @return void - */ - protected function parseArguments(array $argv) { - - $positional = array(); - $options = array(); - - for($ii=0; $ii < count($argv); $ii++) { - - // Skipping the first argument. - if ($ii===0) continue; - - $v = $argv[$ii]; - - if (substr($v,0,2)==='--') { - // This is a long-form option. - $optionName = substr($v,2); - $optionValue = true; - if (strpos($optionName,'=')) { - list($optionName, $optionValue) = explode('=', $optionName); - } - $options[$optionName] = $optionValue; - } elseif (substr($v,0,1) === '-' && strlen($v)>1) { - // This is a short-form option. - foreach(str_split(substr($v,1)) as $option) { - $options[$option] = true; - } - - } else { - - $positional[] = $v; - - } - - } - - return array($options, $positional); - - } - - protected $parser; - - /** - * Reads the input file - * - * @return Component - */ - protected function readInput() { - - if (!$this->parser) { - if ($this->inputPath!=='-') { - $this->stdin = fopen($this->inputPath,'r'); - } - - if ($this->inputFormat === 'mimedir') { - $this->parser = new Parser\MimeDir($this->stdin, ($this->forgiving?Reader::OPTION_FORGIVING:0)); - } else { - $this->parser = new Parser\Json($this->stdin, ($this->forgiving?Reader::OPTION_FORGIVING:0)); - } - } - - return $this->parser->parse(); - - } - - /** - * Sends a message to STDERR. - * - * @param string $msg - * @return void - */ - protected function log($msg, $color = 'default') { - - if (!$this->quiet) { - if ($color!=='default') { - $msg = $this->colorize($color, $msg); - } - fwrite($this->stderr, $msg . "\n"); - } - - } - -}
--- a/vendor/sabre/vobject/lib/Component.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,595 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Component - * - * A component represents a group of properties, such as VCALENDAR, VEVENT, or - * VCARD. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Component extends Node { - - /** - * Component name. - * - * This will contain a string such as VEVENT, VTODO, VCALENDAR, VCARD. - * - * @var string - */ - public $name; - - /** - * A list of properties and/or sub-components. - * - * @var array - */ - public $children = array(); - - /** - * Creates a new component. - * - * You can specify the children either in key=>value syntax, in which case - * properties will automatically be created, or you can just pass a list of - * Component and Property object. - * - * By default, a set of sensible values will be added to the component. For - * an iCalendar object, this may be something like CALSCALE:GREGORIAN. To - * ensure that this does not happen, set $defaults to false. - * - * @param Document $root - * @param string $name such as VCALENDAR, VEVENT. - * @param array $children - * @param bool $defaults - * @return void - */ - function __construct(Document $root, $name, array $children = array(), $defaults = true) { - - $this->name = strtoupper($name); - $this->root = $root; - - if ($defaults) { - // This is a terribly convoluted way to do this, but this ensures - // that the order of properties as they are specified in both - // defaults and the childrens list, are inserted in the object in a - // natural way. - $list = $this->getDefaults(); - $nodes = array(); - foreach($children as $key=>$value) { - if ($value instanceof Node) { - if (isset($list[$value->name])) { - unset($list[$value->name]); - } - $nodes[] = $value; - } else { - $list[$key] = $value; - } - } - foreach($list as $key=>$value) { - $this->add($key, $value); - } - foreach($nodes as $node) { - $this->add($node); - } - } else { - foreach($children as $k=>$child) { - if ($child instanceof Node) { - - // Component or Property - $this->add($child); - } else { - - // Property key=>value - $this->add($k, $child); - } - } - } - - } - - /** - * Adds a new property or component, and returns the new item. - * - * This method has 3 possible signatures: - * - * add(Component $comp) // Adds a new component - * add(Property $prop) // Adds a new property - * add($name, $value, array $parameters = array()) // Adds a new property - * add($name, array $children = array()) // Adds a new component - * by name. - * - * @return Node - */ - function add($a1, $a2 = null, $a3 = null) { - - if ($a1 instanceof Node) { - if (!is_null($a2)) { - throw new \InvalidArgumentException('The second argument must not be specified, when passing a VObject Node'); - } - $a1->parent = $this; - $this->children[] = $a1; - - return $a1; - - } elseif(is_string($a1)) { - - $item = $this->root->create($a1, $a2, $a3); - $item->parent = $this; - $this->children[] = $item; - - return $item; - - } else { - - throw new \InvalidArgumentException('The first argument must either be a \\Sabre\\VObject\\Node or a string'); - - } - - } - - /** - * This method removes a component or property from this component. - * - * You can either specify the item by name (like DTSTART), in which case - * all properties/components with that name will be removed, or you can - * pass an instance of a property or component, in which case only that - * exact item will be removed. - * - * The removed item will be returned. In case there were more than 1 items - * removed, only the last one will be returned. - * - * @param mixed $item - * @return void - */ - function remove($item) { - - if (is_string($item)) { - $children = $this->select($item); - foreach($children as $k=>$child) { - unset($this->children[$k]); - } - return $child; - } else { - foreach($this->children as $k => $child) { - if ($child===$item) { - unset($this->children[$k]); - return $child; - } - } - - throw new \InvalidArgumentException('The item you passed to remove() was not a child of this component'); - - } - - } - - /** - * Returns an iterable list of children - * - * @return array - */ - function children() { - - return $this->children; - - } - - /** - * This method only returns a list of sub-components. Properties are - * ignored. - * - * @return array - */ - function getComponents() { - - $result = array(); - foreach($this->children as $child) { - if ($child instanceof Component) { - $result[] = $child; - } - } - - return $result; - - } - - /** - * Returns an array with elements that match the specified name. - * - * This function is also aware of MIME-Directory groups (as they appear in - * vcards). This means that if a property is grouped as "HOME.EMAIL", it - * will also be returned when searching for just "EMAIL". If you want to - * search for a property in a specific group, you can select on the entire - * string ("HOME.EMAIL"). If you want to search on a specific property that - * has not been assigned a group, specify ".EMAIL". - * - * Keys are retained from the 'children' array, which may be confusing in - * certain cases. - * - * @param string $name - * @return array - */ - function select($name) { - - $group = null; - $name = strtoupper($name); - if (strpos($name,'.')!==false) { - list($group,$name) = explode('.', $name, 2); - } - - $result = array(); - foreach($this->children as $key=>$child) { - - if ( - ( - strtoupper($child->name) === $name - && (is_null($group) || ( $child instanceof Property && strtoupper($child->group) === $group)) - ) - || - ( - $name === '' && $child instanceof Property && strtoupper($child->group) === $group - ) - ) { - - $result[$key] = $child; - - } - } - - reset($result); - return $result; - - } - - /** - * Turns the object back into a serialized blob. - * - * @return string - */ - function serialize() { - - $str = "BEGIN:" . $this->name . "\r\n"; - - /** - * Gives a component a 'score' for sorting purposes. - * - * This is solely used by the childrenSort method. - * - * A higher score means the item will be lower in the list. - * To avoid score collisions, each "score category" has a reasonable - * space to accomodate elements. The $key is added to the $score to - * preserve the original relative order of elements. - * - * @param int $key - * @param array $array - * @return int - */ - $sortScore = function($key, $array) { - - if ($array[$key] instanceof Component) { - - // We want to encode VTIMEZONE first, this is a personal - // preference. - if ($array[$key]->name === 'VTIMEZONE') { - $score=300000000; - return $score+$key; - } else { - $score=400000000; - return $score+$key; - } - } else { - // Properties get encoded first - // VCARD version 4.0 wants the VERSION property to appear first - if ($array[$key] instanceof Property) { - if ($array[$key]->name === 'VERSION') { - $score=100000000; - return $score+$key; - } else { - // All other properties - $score=200000000; - return $score+$key; - } - } - } - - }; - - $tmp = $this->children; - uksort( - $this->children, - function($a, $b) use ($sortScore, $tmp) { - - $sA = $sortScore($a, $tmp); - $sB = $sortScore($b, $tmp); - - return $sA - $sB; - - } - ); - - foreach($this->children as $child) $str.=$child->serialize(); - $str.= "END:" . $this->name . "\r\n"; - - return $str; - - } - - /** - * This method returns an array, with the representation as it should be - * encoded in json. This is used to create jCard or jCal documents. - * - * @return array - */ - function jsonSerialize() { - - $components = array(); - $properties = array(); - - foreach($this->children as $child) { - if ($child instanceof Component) { - $components[] = $child->jsonSerialize(); - } else { - $properties[] = $child->jsonSerialize(); - } - } - - return array( - strtolower($this->name), - $properties, - $components - ); - - } - - /** - * This method should return a list of default property values. - * - * @return array - */ - protected function getDefaults() { - - return array(); - - } - - /* Magic property accessors {{{ */ - - /** - * Using 'get' you will either get a property or component. - * - * If there were no child-elements found with the specified name, - * null is returned. - * - * To use this, this may look something like this: - * - * $event = $calendar->VEVENT; - * - * @param string $name - * @return Property - */ - function __get($name) { - - $matches = $this->select($name); - if (count($matches)===0) { - return null; - } else { - $firstMatch = current($matches); - /** @var $firstMatch Property */ - $firstMatch->setIterator(new ElementList(array_values($matches))); - return $firstMatch; - } - - } - - /** - * This method checks if a sub-element with the specified name exists. - * - * @param string $name - * @return bool - */ - function __isset($name) { - - $matches = $this->select($name); - return count($matches)>0; - - } - - /** - * Using the setter method you can add properties or subcomponents - * - * You can either pass a Component, Property - * object, or a string to automatically create a Property. - * - * If the item already exists, it will be removed. If you want to add - * a new item with the same name, always use the add() method. - * - * @param string $name - * @param mixed $value - * @return void - */ - function __set($name, $value) { - - $matches = $this->select($name); - $overWrite = count($matches)?key($matches):null; - - if ($value instanceof Component || $value instanceof Property) { - $value->parent = $this; - if (!is_null($overWrite)) { - $this->children[$overWrite] = $value; - } else { - $this->children[] = $value; - } - } else { - $property = $this->root->create($name,$value); - $property->parent = $this; - if (!is_null($overWrite)) { - $this->children[$overWrite] = $property; - } else { - $this->children[] = $property; - } - } - } - - /** - * Removes all properties and components within this component with the - * specified name. - * - * @param string $name - * @return void - */ - function __unset($name) { - - $matches = $this->select($name); - foreach($matches as $k=>$child) { - - unset($this->children[$k]); - $child->parent = null; - - } - - } - - /* }}} */ - - /** - * This method is automatically called when the object is cloned. - * Specifically, this will ensure all child elements are also cloned. - * - * @return void - */ - function __clone() { - - foreach($this->children as $key=>$child) { - $this->children[$key] = clone $child; - $this->children[$key]->parent = $this; - } - - } - - /** - * A simple list of validation rules. - * - * This is simply a list of properties, and how many times they either - * must or must not appear. - * - * Possible values per property: - * * 0 - Must not appear. - * * 1 - Must appear exactly once. - * * + - Must appear at least once. - * * * - Can appear any number of times. - * * ? - May appear, but not more than once. - * - * It is also possible to specify defaults and severity levels for - * violating the rule. - * - * See the VEVENT implementation for getValidationRules for a more complex - * example. - * - * @var array - */ - function getValidationRules() { - - return array(); - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * Node::REPAIR - May attempt to automatically repair the problem. - * Node::PROFILE_CARDDAV - Validate the vCard for CardDAV purposes. - * Node::PROFILE_CALDAV - Validate the iCalendar for CalDAV purposes. - * - * This method returns an array with detected problems. - * Every element has the following properties: - * - * * level - problem level. - * * message - A human-readable string describing the issue. - * * node - A reference to the problematic node. - * - * The level means: - * 1 - The issue was repaired (only happens if REPAIR was turned on). - * 2 - A warning. - * 3 - An error. - * - * @param int $options - * @return array - */ - function validate($options = 0) { - - $rules = $this->getValidationRules(); - $defaults = $this->getDefaults(); - - $propertyCounters = array(); - - $messages = array(); - - foreach($this->children as $child) { - $name = strtoupper($child->name); - if (!isset($propertyCounters[$name])) { - $propertyCounters[$name] = 1; - } else { - $propertyCounters[$name]++; - } - $messages = array_merge($messages, $child->validate($options)); - } - - foreach($rules as $propName => $rule) { - - switch($rule) { - case '0' : - if (isset($propertyCounters[$propName])) { - $messages[] = array( - 'level' => 3, - 'message' => $propName . ' MUST NOT appear in a ' . $this->name . ' component', - 'node' => $this, - ); - } - break; - case '1' : - if (!isset($propertyCounters[$propName]) || $propertyCounters[$propName]!==1) { - $repaired = false; - if ($options & self::REPAIR && isset($defaults[$propName])) { - $this->add($propName, $defaults[$propName]); - } - $messages[] = array( - 'level' => $repaired?1:3, - 'message' => $propName . ' MUST appear exactly once in a ' . $this->name . ' component', - 'node' => $this, - ); - } - break; - case '+' : - if (!isset($propertyCounters[$propName]) || $propertyCounters[$propName] < 1) { - $messages[] = array( - 'level' => 3, - 'message' => $propName . ' MUST appear at least once in a ' . $this->name . ' component', - 'node' => $this, - ); - } - break; - case '*' : - break; - case '?' : - if (isset($propertyCounters[$propName]) && $propertyCounters[$propName] > 1) { - $messages[] = array( - 'level' => 3, - 'message' => $propName . ' MUST NOT appear more than once in a ' . $this->name . ' component', - 'node' => $this, - ); - } - break; - - } - - } - return $messages; - - } - -}
--- a/vendor/sabre/vobject/lib/Component/VAlarm.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,136 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; -use Sabre\VObject; - -/** - * VAlarm component - * - * This component contains some additional functionality specific for VALARMs. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class VAlarm extends VObject\Component { - - /** - * Returns a DateTime object when this alarm is going to trigger. - * - * This ignores repeated alarm, only the first trigger is returned. - * - * @return DateTime - */ - public function getEffectiveTriggerTime() { - - $trigger = $this->TRIGGER; - if(!isset($trigger['VALUE']) || strtoupper($trigger['VALUE']) === 'DURATION') { - $triggerDuration = VObject\DateTimeParser::parseDuration($this->TRIGGER); - $related = (isset($trigger['RELATED']) && strtoupper($trigger['RELATED']) == 'END') ? 'END' : 'START'; - - $parentComponent = $this->parent; - if ($related === 'START') { - - if ($parentComponent->name === 'VTODO') { - $propName = 'DUE'; - } else { - $propName = 'DTSTART'; - } - - $effectiveTrigger = clone $parentComponent->$propName->getDateTime(); - $effectiveTrigger->add($triggerDuration); - } else { - if ($parentComponent->name === 'VTODO') { - $endProp = 'DUE'; - } elseif ($parentComponent->name === 'VEVENT') { - $endProp = 'DTEND'; - } else { - throw new \LogicException('time-range filters on VALARM components are only supported when they are a child of VTODO or VEVENT'); - } - - if (isset($parentComponent->$endProp)) { - $effectiveTrigger = clone $parentComponent->$endProp->getDateTime(); - $effectiveTrigger->add($triggerDuration); - } elseif (isset($parentComponent->DURATION)) { - $effectiveTrigger = clone $parentComponent->DTSTART->getDateTime(); - $duration = VObject\DateTimeParser::parseDuration($parentComponent->DURATION); - $effectiveTrigger->add($duration); - $effectiveTrigger->add($triggerDuration); - } else { - $effectiveTrigger = clone $parentComponent->DTSTART->getDateTime(); - $effectiveTrigger->add($triggerDuration); - } - } - } else { - $effectiveTrigger = $trigger->getDateTime(); - } - return $effectiveTrigger; - - } - - /** - * Returns true or false depending on if the event falls in the specified - * time-range. This is used for filtering purposes. - * - * The rules used to determine if an event falls within the specified - * time-range is based on the CalDAV specification. - * - * @param \DateTime $start - * @param \DateTime $end - * @return bool - */ - public function isInTimeRange(\DateTime $start, \DateTime $end) { - - $effectiveTrigger = $this->getEffectiveTriggerTime(); - - if (isset($this->DURATION)) { - $duration = VObject\DateTimeParser::parseDuration($this->DURATION); - $repeat = (string)$this->repeat; - if (!$repeat) { - $repeat = 1; - } - - $period = new \DatePeriod($effectiveTrigger, $duration, (int)$repeat); - - foreach($period as $occurrence) { - - if ($start <= $occurrence && $end > $occurrence) { - return true; - } - } - return false; - } else { - return ($start <= $effectiveTrigger && $end > $effectiveTrigger); - } - - } - - /** - * A simple list of validation rules. - * - * This is simply a list of properties, and how many times they either - * must or must not appear. - * - * Possible values per property: - * * 0 - Must not appear. - * * 1 - Must appear exactly once. - * * + - Must appear at least once. - * * * - Can appear any number of times. - * - * @var array - */ - public function getValidationRules() { - - return array( - 'ACTION' => 1, - 'TRIGGER' => 1, - - 'DURATION' => '?', - 'REPEAT' => '?', - - 'ATTACH' => '?', - ); - - } - -}
--- a/vendor/sabre/vobject/lib/Component/VCalendar.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,490 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use DateTime; -use DateTimeZone; -use Sabre\VObject; -use Sabre\VObject\Component; -use Sabre\VObject\Recur\EventIterator; -use Sabre\VObject\Recur\NoInstancesException; - -/** - * The VCalendar component - * - * This component adds functionality to a component, specific for a VCALENDAR. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class VCalendar extends VObject\Document { - - /** - * The default name for this component. - * - * This should be 'VCALENDAR' or 'VCARD'. - * - * @var string - */ - static $defaultName = 'VCALENDAR'; - - /** - * This is a list of components, and which classes they should map to. - * - * @var array - */ - static $componentMap = array( - 'VALARM' => 'Sabre\\VObject\\Component\\VAlarm', - 'VEVENT' => 'Sabre\\VObject\\Component\\VEvent', - 'VFREEBUSY' => 'Sabre\\VObject\\Component\\VFreeBusy', - 'VJOURNAL' => 'Sabre\\VObject\\Component\\VJournal', - 'VTIMEZONE' => 'Sabre\\VObject\\Component\\VTimeZone', - 'VTODO' => 'Sabre\\VObject\\Component\\VTodo', - ); - - /** - * List of value-types, and which classes they map to. - * - * @var array - */ - static $valueMap = array( - 'BINARY' => 'Sabre\\VObject\\Property\\Binary', - 'BOOLEAN' => 'Sabre\\VObject\\Property\\Boolean', - 'CAL-ADDRESS' => 'Sabre\\VObject\\Property\\ICalendar\\CalAddress', - 'DATE' => 'Sabre\\VObject\\Property\\ICalendar\\Date', - 'DATE-TIME' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'DURATION' => 'Sabre\\VObject\\Property\\ICalendar\\Duration', - 'FLOAT' => 'Sabre\\VObject\\Property\\Float', - 'INTEGER' => 'Sabre\\VObject\\Property\\Integer', - 'PERIOD' => 'Sabre\\VObject\\Property\\ICalendar\\Period', - 'RECUR' => 'Sabre\\VObject\\Property\\ICalendar\\Recur', - 'TEXT' => 'Sabre\\VObject\\Property\\Text', - 'TIME' => 'Sabre\\VObject\\Property\\Time', - 'UNKNOWN' => 'Sabre\\VObject\\Property\\Unknown', // jCard / jCal-only. - 'URI' => 'Sabre\\VObject\\Property\\Uri', - 'UTC-OFFSET' => 'Sabre\\VObject\\Property\\UtcOffset', - ); - - /** - * List of properties, and which classes they map to. - * - * @var array - */ - static $propertyMap = array( - // Calendar properties - 'CALSCALE' => 'Sabre\\VObject\\Property\\FlatText', - 'METHOD' => 'Sabre\\VObject\\Property\\FlatText', - 'PRODID' => 'Sabre\\VObject\\Property\\FlatText', - 'VERSION' => 'Sabre\\VObject\\Property\\FlatText', - - // Component properties - 'ATTACH' => 'Sabre\\VObject\\Property\\Uri', - 'CATEGORIES' => 'Sabre\\VObject\\Property\\Text', - 'CLASS' => 'Sabre\\VObject\\Property\\FlatText', - 'COMMENT' => 'Sabre\\VObject\\Property\\FlatText', - 'DESCRIPTION' => 'Sabre\\VObject\\Property\\FlatText', - 'GEO' => 'Sabre\\VObject\\Property\\Float', - 'LOCATION' => 'Sabre\\VObject\\Property\\FlatText', - 'PERCENT-COMPLETE' => 'Sabre\\VObject\\Property\\Integer', - 'PRIORITY' => 'Sabre\\VObject\\Property\\Integer', - 'RESOURCES' => 'Sabre\\VObject\\Property\\Text', - 'STATUS' => 'Sabre\\VObject\\Property\\FlatText', - 'SUMMARY' => 'Sabre\\VObject\\Property\\FlatText', - - // Date and Time Component Properties - 'COMPLETED' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'DTEND' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'DUE' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'DTSTART' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'DURATION' => 'Sabre\\VObject\\Property\\ICalendar\\Duration', - 'FREEBUSY' => 'Sabre\\VObject\\Property\\ICalendar\\Period', - 'TRANSP' => 'Sabre\\VObject\\Property\\FlatText', - - // Time Zone Component Properties - 'TZID' => 'Sabre\\VObject\\Property\\FlatText', - 'TZNAME' => 'Sabre\\VObject\\Property\\FlatText', - 'TZOFFSETFROM' => 'Sabre\\VObject\\Property\\UtcOffset', - 'TZOFFSETTO' => 'Sabre\\VObject\\Property\\UtcOffset', - 'TZURL' => 'Sabre\\VObject\\Property\\Uri', - - // Relationship Component Properties - 'ATTENDEE' => 'Sabre\\VObject\\Property\\ICalendar\\CalAddress', - 'CONTACT' => 'Sabre\\VObject\\Property\\FlatText', - 'ORGANIZER' => 'Sabre\\VObject\\Property\\ICalendar\\CalAddress', - 'RECURRENCE-ID' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'RELATED-TO' => 'Sabre\\VObject\\Property\\FlatText', - 'URL' => 'Sabre\\VObject\\Property\\Uri', - 'UID' => 'Sabre\\VObject\\Property\\FlatText', - - // Recurrence Component Properties - 'EXDATE' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'RDATE' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'RRULE' => 'Sabre\\VObject\\Property\\ICalendar\\Recur', - 'EXRULE' => 'Sabre\\VObject\\Property\\ICalendar\\Recur', // Deprecated since rfc5545 - - // Alarm Component Properties - 'ACTION' => 'Sabre\\VObject\\Property\\FlatText', - 'REPEAT' => 'Sabre\\VObject\\Property\\Integer', - 'TRIGGER' => 'Sabre\\VObject\\Property\\ICalendar\\Duration', - - // Change Management Component Properties - 'CREATED' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'DTSTAMP' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'LAST-MODIFIED' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'SEQUENCE' => 'Sabre\\VObject\\Property\\Integer', - - // Request Status - 'REQUEST-STATUS' => 'Sabre\\VObject\\Property\\Text', - - // Additions from draft-daboo-valarm-extensions-04 - 'ALARM-AGENT' => 'Sabre\\VObject\\Property\\Text', - 'ACKNOWLEDGED' => 'Sabre\\VObject\\Property\\ICalendar\\DateTime', - 'PROXIMITY' => 'Sabre\\VObject\\Property\\Text', - 'DEFAULT-ALARM' => 'Sabre\\VObject\\Property\\Boolean', - - ); - - /** - * Returns the current document type. - * - * @return void - */ - function getDocumentType() { - - return self::ICALENDAR20; - - } - - /** - * Returns a list of all 'base components'. For instance, if an Event has - * a recurrence rule, and one instance is overridden, the overridden event - * will have the same UID, but will be excluded from this list. - * - * VTIMEZONE components will always be excluded. - * - * @param string $componentName filter by component name - * @return VObject\Component[] - */ - function getBaseComponents($componentName = null) { - - $components = array(); - foreach($this->children as $component) { - - if (!$component instanceof VObject\Component) - continue; - - if (isset($component->{'RECURRENCE-ID'})) - continue; - - if ($componentName && $component->name !== strtoupper($componentName)) - continue; - - if ($component->name === 'VTIMEZONE') - continue; - - $components[] = $component; - - } - - return $components; - - } - - /** - * Returns the first component that is not a VTIMEZONE, and does not have - * an RECURRENCE-ID. - * - * If there is no such component, null will be returned. - * - * @param string $componentName filter by component name - * @return VObject\Component|null - */ - function getBaseComponent($componentName = null) { - - foreach($this->children as $component) { - - if (!$component instanceof VObject\Component) - continue; - - if (isset($component->{'RECURRENCE-ID'})) - continue; - - if ($componentName && $component->name !== strtoupper($componentName)) - continue; - - if ($component->name === 'VTIMEZONE') - continue; - - return $component; - - } - - } - - /** - * If this calendar object, has events with recurrence rules, this method - * can be used to expand the event into multiple sub-events. - * - * Each event will be stripped from it's recurrence information, and only - * the instances of the event in the specified timerange will be left - * alone. - * - * In addition, this method will cause timezone information to be stripped, - * and normalized to UTC. - * - * This method will alter the VCalendar. This cannot be reversed. - * - * This functionality is specifically used by the CalDAV standard. It is - * possible for clients to request expand events, if they are rather simple - * clients and do not have the possibility to calculate recurrences. - * - * @param DateTime $start - * @param DateTime $end - * @param DateTimeZone $timeZone reference timezone for floating dates and - * times. - * @return void - */ - function expand(DateTime $start, DateTime $end, DateTimeZone $timeZone = null) { - - $newEvents = array(); - - if (!$timeZone) { - $timeZone = new DateTimeZone('UTC'); - } - - foreach($this->select('VEVENT') as $key=>$vevent) { - - if (isset($vevent->{'RECURRENCE-ID'})) { - unset($this->children[$key]); - continue; - } - - - if (!$vevent->rrule) { - unset($this->children[$key]); - if ($vevent->isInTimeRange($start, $end)) { - $newEvents[] = $vevent; - } - continue; - } - - - - $uid = (string)$vevent->uid; - if (!$uid) { - throw new \LogicException('Event did not have a UID!'); - } - - try { - $it = new EventIterator($this, $vevent->uid, $timeZone); - } catch (NoInstancesException $e) { - // This event is recurring, but it doesn't have a single - // instance. We are skipping this event from the output - // entirely. - unset($this->children[$key]); - continue; - } - $it->fastForward($start); - - while($it->valid() && $it->getDTStart() < $end) { - - if ($it->getDTEnd() > $start) { - - $newEvents[] = $it->getEventObject(); - - } - $it->next(); - - } - - unset($this->children[$key]); - - } - - // Setting all properties to UTC time. - foreach($newEvents as $newEvent) { - - foreach($newEvent->children as $child) { - if ($child instanceof VObject\Property\ICalendar\DateTime && $child->hasTime()) { - $dt = $child->getDateTimes($timeZone); - // We only need to update the first timezone, because - // setDateTimes will match all other timezones to the - // first. - $dt[0]->setTimeZone(new DateTimeZone('UTC')); - $child->setDateTimes($dt); - } - - } - - $this->add($newEvent); - - } - - // Removing all VTIMEZONE components - unset($this->VTIMEZONE); - - } - - /** - * This method should return a list of default property values. - * - * @return array - */ - protected function getDefaults() { - - return array( - 'VERSION' => '2.0', - 'PRODID' => '-//Sabre//Sabre VObject ' . VObject\Version::VERSION . '//EN', - 'CALSCALE' => 'GREGORIAN', - ); - - } - - /** - * A simple list of validation rules. - * - * This is simply a list of properties, and how many times they either - * must or must not appear. - * - * Possible values per property: - * * 0 - Must not appear. - * * 1 - Must appear exactly once. - * * + - Must appear at least once. - * * * - Can appear any number of times. - * - * @var array - */ - function getValidationRules() { - - return array( - 'PRODID' => 1, - 'VERSION' => 1, - - 'CALSCALE' => '?', - 'METHOD' => '?', - ); - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * Node::REPAIR - May attempt to automatically repair the problem. - * Node::PROFILE_CARDDAV - Validate the vCard for CardDAV purposes. - * Node::PROFILE_CALDAV - Validate the iCalendar for CalDAV purposes. - * - * This method returns an array with detected problems. - * Every element has the following properties: - * - * * level - problem level. - * * message - A human-readable string describing the issue. - * * node - A reference to the problematic node. - * - * The level means: - * 1 - The issue was repaired (only happens if REPAIR was turned on). - * 2 - A warning. - * 3 - An error. - * - * @param int $options - * @return array - */ - function validate($options = 0) { - - $warnings = parent::validate($options); - - if ($ver = $this->VERSION) { - if ((string)$ver !== '2.0') { - $warnings[] = array( - 'level' => 3, - 'message' => 'Only iCalendar version 2.0 as defined in rfc5545 is supported.', - 'node' => $this, - ); - } - - } - - $uidList = array(); - - $componentsFound = 0; - - $componentTypes = array(); - - foreach($this->children as $child) { - if($child instanceof Component) { - $componentsFound++; - - if (!in_array($child->name, array('VEVENT', 'VTODO', 'VJOURNAL'))) { - continue; - } - $componentTypes[] = $child->name; - - $uid = (string)$child->UID; - $isMaster = isset($child->{'RECURRENCE-ID'})?0:1; - if (isset($uidList[$uid])) { - $uidList[$uid]['count']++; - if ($isMaster && $uidList[$uid]['hasMaster']) { - $warnings[] = array( - 'level' => 3, - 'message' => 'More than one master object was found for the object with UID ' . $uid, - 'node' => $this, - ); - } - $uidList[$uid]['hasMaster']+=$isMaster; - } else { - $uidList[$uid] = array( - 'count' => 1, - 'hasMaster' => $isMaster, - ); - } - - } - } - - if ($componentsFound===0) { - $warnings[] = array( - 'level' => 3, - 'message' => 'An iCalendar object must have at least 1 component.', - 'node' => $this, - ); - } - - if ($options & self::PROFILE_CALDAV) { - if (count($uidList)>1) { - $warnings[] = array( - 'level' => 3, - 'message' => 'A calendar object on a CalDAV server may only have components with the same UID.', - 'node' => $this, - ); - } - if (count(array_unique($componentTypes))===0) { - $warnings[] = array( - 'level' => 3, - 'message' => 'A calendar object on a CalDAV server must have at least 1 component (VTODO, VEVENT, VJOURNAL).', - 'node' => $this, - ); - } - if (count(array_unique($componentTypes))>1) { - $warnings[] = array( - 'level' => 3, - 'message' => 'A calendar object on a CalDAV server may only have 1 type of component (VEVENT, VTODO or VJOURNAL).', - 'node' => $this, - ); - } - - if (isset($this->METHOD)) { - $warnings[] = array( - 'level' => 3, - 'message' => 'A calendar object on a CalDAV server MUST NOT have a METHOD property.', - 'node' => $this, - ); - } - } - - return $warnings; - - } - -} -
--- a/vendor/sabre/vobject/lib/Component/VCard.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,451 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use - Sabre\VObject; - -/** - * The VCard component - * - * This component represents the BEGIN:VCARD and END:VCARD found in every - * vcard. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class VCard extends VObject\Document { - - /** - * The default name for this component. - * - * This should be 'VCALENDAR' or 'VCARD'. - * - * @var string - */ - static $defaultName = 'VCARD'; - - /** - * Caching the version number - * - * @var int - */ - private $version = null; - - /** - * List of value-types, and which classes they map to. - * - * @var array - */ - static $valueMap = array( - 'BINARY' => 'Sabre\\VObject\\Property\\Binary', - 'BOOLEAN' => 'Sabre\\VObject\\Property\\Boolean', - 'CONTENT-ID' => 'Sabre\\VObject\\Property\\FlatText', // vCard 2.1 only - 'DATE' => 'Sabre\\VObject\\Property\\VCard\\Date', - 'DATE-TIME' => 'Sabre\\VObject\\Property\\VCard\\DateTime', - 'DATE-AND-OR-TIME' => 'Sabre\\VObject\\Property\\VCard\\DateAndOrTime', // vCard only - 'FLOAT' => 'Sabre\\VObject\\Property\\Float', - 'INTEGER' => 'Sabre\\VObject\\Property\\Integer', - 'LANGUAGE-TAG' => 'Sabre\\VObject\\Property\\VCard\\LanguageTag', - 'TIMESTAMP' => 'Sabre\\VObject\\Property\\VCard\\TimeStamp', - 'TEXT' => 'Sabre\\VObject\\Property\\Text', - 'TIME' => 'Sabre\\VObject\\Property\\Time', - 'UNKNOWN' => 'Sabre\\VObject\\Property\\Unknown', // jCard / jCal-only. - 'URI' => 'Sabre\\VObject\\Property\\Uri', - 'URL' => 'Sabre\\VObject\\Property\\Uri', // vCard 2.1 only - 'UTC-OFFSET' => 'Sabre\\VObject\\Property\\UtcOffset', - ); - - /** - * List of properties, and which classes they map to. - * - * @var array - */ - static $propertyMap = array( - - // vCard 2.1 properties and up - 'N' => 'Sabre\\VObject\\Property\\Text', - 'FN' => 'Sabre\\VObject\\Property\\FlatText', - 'PHOTO' => 'Sabre\\VObject\\Property\\Binary', // Todo: we should add a class for Binary values. - 'BDAY' => 'Sabre\\VObject\\Property\\VCard\\DateAndOrTime', - 'ADR' => 'Sabre\\VObject\\Property\\Text', - 'LABEL' => 'Sabre\\VObject\\Property\\FlatText', // Removed in vCard 4.0 - 'TEL' => 'Sabre\\VObject\\Property\\FlatText', - 'EMAIL' => 'Sabre\\VObject\\Property\\FlatText', - 'MAILER' => 'Sabre\\VObject\\Property\\FlatText', // Removed in vCard 4.0 - 'GEO' => 'Sabre\\VObject\\Property\\FlatText', - 'TITLE' => 'Sabre\\VObject\\Property\\FlatText', - 'ROLE' => 'Sabre\\VObject\\Property\\FlatText', - 'LOGO' => 'Sabre\\VObject\\Property\\Binary', - // 'AGENT' => 'Sabre\\VObject\\Property\\', // Todo: is an embedded vCard. Probably rare, so - // not supported at the moment - 'ORG' => 'Sabre\\VObject\\Property\\Text', - 'NOTE' => 'Sabre\\VObject\\Property\\FlatText', - 'REV' => 'Sabre\\VObject\\Property\\VCard\\TimeStamp', - 'SOUND' => 'Sabre\\VObject\\Property\\FlatText', - 'URL' => 'Sabre\\VObject\\Property\\Uri', - 'UID' => 'Sabre\\VObject\\Property\\FlatText', - 'VERSION' => 'Sabre\\VObject\\Property\\FlatText', - 'KEY' => 'Sabre\\VObject\\Property\\FlatText', - 'TZ' => 'Sabre\\VObject\\Property\\Text', - - // vCard 3.0 properties - 'CATEGORIES' => 'Sabre\\VObject\\Property\\Text', - 'SORT-STRING' => 'Sabre\\VObject\\Property\\FlatText', - 'PRODID' => 'Sabre\\VObject\\Property\\FlatText', - 'NICKNAME' => 'Sabre\\VObject\\Property\\Text', - 'CLASS' => 'Sabre\\VObject\\Property\\FlatText', // Removed in vCard 4.0 - - // rfc2739 properties - 'FBURL' => 'Sabre\\VObject\\Property\\Uri', - 'CAPURI' => 'Sabre\\VObject\\Property\\Uri', - 'CALURI' => 'Sabre\\VObject\\Property\\Uri', - - // rfc4770 properties - 'IMPP' => 'Sabre\\VObject\\Property\\Uri', - - // vCard 4.0 properties - 'XML' => 'Sabre\\VObject\\Property\\FlatText', - 'ANNIVERSARY' => 'Sabre\\VObject\\Property\\VCard\\DateAndOrTime', - 'CLIENTPIDMAP' => 'Sabre\\VObject\\Property\\Text', - 'LANG' => 'Sabre\\VObject\\Property\\VCard\\LanguageTag', - 'GENDER' => 'Sabre\\VObject\\Property\\Text', - 'KIND' => 'Sabre\\VObject\\Property\\FlatText', - - // rfc6474 properties - 'BIRTHPLACE' => 'Sabre\\VObject\\Property\\FlatText', - 'DEATHPLACE' => 'Sabre\\VObject\\Property\\FlatText', - 'DEATHDATE' => 'Sabre\\VObject\\Property\\VCard\\DateAndOrTime', - - // rfc6715 properties - 'EXPERTISE' => 'Sabre\\VObject\\Property\\FlatText', - 'HOBBY' => 'Sabre\\VObject\\Property\\FlatText', - 'INTEREST' => 'Sabre\\VObject\\Property\\FlatText', - 'ORG-DIRECTORY' => 'Sabre\\VObject\\Property\\FlatText', - - ); - - /** - * Returns the current document type. - * - * @return void - */ - function getDocumentType() { - - if (!$this->version) { - $version = (string)$this->VERSION; - switch($version) { - case '2.1' : - $this->version = self::VCARD21; - break; - case '3.0' : - $this->version = self::VCARD30; - break; - case '4.0' : - $this->version = self::VCARD40; - break; - default : - $this->version = self::UNKNOWN; - break; - - } - } - - return $this->version; - - } - - /** - * Converts the document to a different vcard version. - * - * Use one of the VCARD constants for the target. This method will return - * a copy of the vcard in the new version. - * - * At the moment the only supported conversion is from 3.0 to 4.0. - * - * If input and output version are identical, a clone is returned. - * - * @param int $target - * @return VCard - */ - function convert($target) { - - $converter = new VObject\VCardConverter(); - return $converter->convert($this, $target); - - } - - /** - * VCards with version 2.1, 3.0 and 4.0 are found. - * - * If the VCARD doesn't know its version, 2.1 is assumed. - */ - const DEFAULT_VERSION = self::VCARD21; - - /** - * Validates the node for correctness. - * - * The following options are supported: - * Node::REPAIR - May attempt to automatically repair the problem. - * - * This method returns an array with detected problems. - * Every element has the following properties: - * - * * level - problem level. - * * message - A human-readable string describing the issue. - * * node - A reference to the problematic node. - * - * The level means: - * 1 - The issue was repaired (only happens if REPAIR was turned on) - * 2 - An inconsequential issue - * 3 - A severe issue. - * - * @param int $options - * @return array - */ - function validate($options = 0) { - - $warnings = array(); - - $versionMap = array( - self::VCARD21 => '2.1', - self::VCARD30 => '3.0', - self::VCARD40 => '4.0', - ); - - $version = $this->select('VERSION'); - if (count($version)===1) { - $version = (string)$this->VERSION; - if ($version!=='2.1' && $version!=='3.0' && $version!=='4.0') { - $warnings[] = array( - 'level' => 3, - 'message' => 'Only vcard version 4.0 (RFC6350), version 3.0 (RFC2426) or version 2.1 (icm-vcard-2.1) are supported.', - 'node' => $this, - ); - if ($options & self::REPAIR) { - $this->VERSION = $versionMap[self::DEFAULT_VERSION]; - } - } - if ($version === '2.1' && ($options & self::PROFILE_CARDDAV)) { - $warnings[] = array( - 'level' => 3, - 'message' => 'CardDAV servers are not allowed to accept vCard 2.1.', - 'node' => $this, - ); - } - - } - $uid = $this->select('UID'); - if (count($uid) === 0) { - if ($options & self::PROFILE_CARDDAV) { - // Required for CardDAV - $warningLevel = 3; - $message = 'vCards on CardDAV servers MUST have a UID property.'; - } else { - // Not required for regular vcards - $warningLevel = 2; - $message = 'Adding a UID to a vCard property is recommended.'; - } - if ($options & self::REPAIR) { - $this->UID = VObject\UUIDUtil::getUUID(); - $warningLevel = 1; - } - $warnings[] = array( - 'level' => $warningLevel, - 'message' => $message, - 'node' => $this, - ); - } - - $fn = $this->select('FN'); - if (count($fn)!==1) { - - $repaired = false; - if (($options & self::REPAIR) && count($fn) === 0) { - // We're going to try to see if we can use the contents of the - // N property. - if (isset($this->N)) { - $value = explode(';', (string)$this->N); - if (isset($value[1]) && $value[1]) { - $this->FN = $value[1] . ' ' . $value[0]; - } else { - $this->FN = $value[0]; - } - $repaired = true; - - // Otherwise, the ORG property may work - } elseif (isset($this->ORG)) { - $this->FN = (string)$this->ORG; - $repaired = true; - } - - } - $warnings[] = array( - 'level' => $repaired?1:3, - 'message' => 'The FN property must appear in the VCARD component exactly 1 time', - 'node' => $this, - ); - } - - return array_merge( - parent::validate($options), - $warnings - ); - - } - - /** - * A simple list of validation rules. - * - * This is simply a list of properties, and how many times they either - * must or must not appear. - * - * Possible values per property: - * * 0 - Must not appear. - * * 1 - Must appear exactly once. - * * + - Must appear at least once. - * * * - Can appear any number of times. - * - * @var array - */ - function getValidationRules() { - - return array( - 'ADR' => '*', - 'ANNIVERSARY' => '?', - 'BDAY' => '?', - 'CALADRURI' => '*', - 'CALURI' => '*', - 'CATEGORIES' => '*', - 'CLIENTPIDMAP' => '*', - 'EMAIL' => '*', - 'FBURL' => '*', - 'IMPP' => '*', - 'GENDER' => '?', - 'GEO' => '*', - 'KEY' => '*', - 'KIND' => '?', - 'LANG' => '*', - 'LOGO' => '*', - 'MEMBER' => '*', - 'N' => '?', - 'NICKNAME' => '*', - 'NOTE' => '*', - 'ORG' => '*', - 'PHOTO' => '*', - 'PRODID' => '?', - 'RELATED' => '*', - 'REV' => '?', - 'ROLE' => '*', - 'SOUND' => '*', - 'SOURCE' => '*', - 'TEL' => '*', - 'TITLE' => '*', - 'TZ' => '*', - 'URL' => '*', - 'VERSION' => '1', - 'XML' => '*', - - // FN is commented out, because it's already handled by the - // validate function, which may also try to repair it. - // 'FN' => '+', - - 'UID' => '?', - ); - - } - - /** - * Returns a preferred field. - * - * VCards can indicate wether a field such as ADR, TEL or EMAIL is - * preferred by specifying TYPE=PREF (vcard 2.1, 3) or PREF=x (vcard 4, x - * being a number between 1 and 100). - * - * If neither of those parameters are specified, the first is returned, if - * a field with that name does not exist, null is returned. - * - * @param string $fieldName - * @return VObject\Property|null - */ - function preferred($propertyName) { - - $preferred = null; - $lastPref = 101; - foreach($this->select($propertyName) as $field) { - - $pref = 101; - if (isset($field['TYPE']) && $field['TYPE']->has('PREF')) { - $pref = 1; - } elseif (isset($field['PREF'])) { - $pref = $field['PREF']->getValue(); - } - - if ($pref < $lastPref || is_null($preferred)) { - $preferred = $field; - $lastPref = $pref; - } - - } - return $preferred; - - } - - /** - * This method should return a list of default property values. - * - * @return array - */ - protected function getDefaults() { - - return array( - 'VERSION' => '3.0', - 'PRODID' => '-//Sabre//Sabre VObject ' . VObject\Version::VERSION . '//EN', - ); - - } - - /** - * This method returns an array, with the representation as it should be - * encoded in json. This is used to create jCard or jCal documents. - * - * @return array - */ - function jsonSerialize() { - - // A vcard does not have sub-components, so we're overriding this - // method to remove that array element. - $properties = array(); - - foreach($this->children as $child) { - $properties[] = $child->jsonSerialize(); - } - - return array( - strtolower($this->name), - $properties, - ); - - } - - /** - * Returns the default class for a property name. - * - * @param string $propertyName - * @return string - */ - function getClassNameForPropertyName($propertyName) { - - $className = parent::getClassNameForPropertyName($propertyName); - // In vCard 4, BINARY no longer exists, and we need URI instead. - - if ($className == 'Sabre\\VObject\\Property\\Binary' && $this->getDocumentType()===self::VCARD40) { - return 'Sabre\\VObject\\Property\\Uri'; - } - return $className; - - } - -} -
--- a/vendor/sabre/vobject/lib/Component/VEvent.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,140 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; -use Sabre\VObject\Recur\EventIterator; - -/** - * VEvent component - * - * This component contains some additional functionality specific for VEVENT's. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class VEvent extends VObject\Component { - - /** - * Returns true or false depending on if the event falls in the specified - * time-range. This is used for filtering purposes. - * - * The rules used to determine if an event falls within the specified - * time-range is based on the CalDAV specification. - * - * @param \DateTime $start - * @param \DateTime $end - * @return bool - */ - public function isInTimeRange(\DateTime $start, \DateTime $end) { - - if ($this->RRULE) { - $it = new EventIterator($this); - $it->fastForward($start); - - // We fast-forwarded to a spot where the end-time of the - // recurrence instance exceeded the start of the requested - // time-range. - // - // If the starttime of the recurrence did not exceed the - // end of the time range as well, we have a match. - return ($it->getDTStart() < $end && $it->getDTEnd() > $start); - - } - - $effectiveStart = $this->DTSTART->getDateTime(); - if (isset($this->DTEND)) { - - // The DTEND property is considered non inclusive. So for a 3 day - // event in july, dtstart and dtend would have to be July 1st and - // July 4th respectively. - // - // See: - // http://tools.ietf.org/html/rfc5545#page-54 - $effectiveEnd = $this->DTEND->getDateTime(); - - } elseif (isset($this->DURATION)) { - $effectiveEnd = clone $effectiveStart; - $effectiveEnd->add(VObject\DateTimeParser::parseDuration($this->DURATION)); - } elseif (!$this->DTSTART->hasTime()) { - $effectiveEnd = clone $effectiveStart; - $effectiveEnd->modify('+1 day'); - } else { - $effectiveEnd = clone $effectiveStart; - } - return ( - ($start <= $effectiveEnd) && ($end > $effectiveStart) - ); - - } - - /** - * This method should return a list of default property values. - * - * @return array - */ - protected function getDefaults() { - - return array( - 'UID' => 'sabre-vobject-' . VObject\UUIDUtil::getUUID(), - 'DTSTAMP' => date('Ymd\\THis\\Z'), - ); - - } - - - /** - * A simple list of validation rules. - * - * This is simply a list of properties, and how many times they either - * must or must not appear. - * - * Possible values per property: - * * 0 - Must not appear. - * * 1 - Must appear exactly once. - * * + - Must appear at least once. - * * * - Can appear any number of times. - * - * @var array - */ - public function getValidationRules() { - - $hasMethod = isset($this->parent->METHOD); - return array( - 'UID' => 1, - 'DTSTAMP' => 1, - 'DTSTART' => $hasMethod?'?':'1', - 'CLASS' => '?', - 'CREATED' => '?', - 'DESCRIPTION' => '?', - 'GEO' => '?', - 'LAST-MODIFICATION' => '?', - 'LOCATION' => '?', - 'ORGANIZER' => '?', - 'PRIORITY' => '?', - 'SEQUENCE' => '?', - 'STATUS' => '?', - 'SUMMARY' => '?', - 'TRANSP' => '?', - 'URL' => '?', - 'RECURRENCE-ID' => '?', - 'RRULE' => '?', - 'DTEND' => '?', - 'DURATION' => '?', - - 'ATTACH' => '*', - 'ATTENDEE' => '*', - 'CATEGORIES' => '*', - 'COMMENT' => '*', - 'CONTACT' => '*', - 'EXDATE' => '*', - 'REQUEST-STATUS' => '*', - 'RELATED-TO' => '*', - 'RESOURCES' => '*', - 'RDATE' => '*', - ); - - } - -}
--- a/vendor/sabre/vobject/lib/Component/VFreeBusy.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,102 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -/** - * The VFreeBusy component - * - * This component adds functionality to a component, specific for VFREEBUSY - * components. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class VFreeBusy extends VObject\Component { - - /** - * Checks based on the contained FREEBUSY information, if a timeslot is - * available. - * - * @param DateTime $start - * @param Datetime $end - * @return bool - */ - public function isFree(\DateTime $start, \Datetime $end) { - - foreach($this->select('FREEBUSY') as $freebusy) { - - // We are only interested in FBTYPE=BUSY (the default), - // FBTYPE=BUSY-TENTATIVE or FBTYPE=BUSY-UNAVAILABLE. - if (isset($freebusy['FBTYPE']) && strtoupper(substr((string)$freebusy['FBTYPE'],0,4))!=='BUSY') { - continue; - } - - // The freebusy component can hold more than 1 value, separated by - // commas. - $periods = explode(',', (string)$freebusy); - - foreach($periods as $period) { - // Every period is formatted as [start]/[end]. The start is an - // absolute UTC time, the end may be an absolute UTC time, or - // duration (relative) value. - list($busyStart, $busyEnd) = explode('/', $period); - - $busyStart = VObject\DateTimeParser::parse($busyStart); - $busyEnd = VObject\DateTimeParser::parse($busyEnd); - if ($busyEnd instanceof \DateInterval) { - $tmp = clone $busyStart; - $tmp->add($busyEnd); - $busyEnd = $tmp; - } - - if($start < $busyEnd && $end > $busyStart) { - return false; - } - - } - - } - - return true; - - } - - /** - * A simple list of validation rules. - * - * This is simply a list of properties, and how many times they either - * must or must not appear. - * - * Possible values per property: - * * 0 - Must not appear. - * * 1 - Must appear exactly once. - * * + - Must appear at least once. - * * * - Can appear any number of times. - * - * @var array - */ - public function getValidationRules() { - - return array( - 'UID' => 1, - 'DTSTAMP' => 1, - - 'CONTACT' => '?', - 'DTSTART' => '?', - 'DTEND' => '?', - 'ORGANIZER' => '?', - 'URL' => '?', - - 'ATTENDEE' => '*', - 'COMMENT' => '*', - 'FREEBUSY' => '*', - 'REQUEST-STATUS' => '*', - ); - - } - -} -
--- a/vendor/sabre/vobject/lib/Component/VJournal.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,90 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -/** - * VJournal component - * - * This component contains some additional functionality specific for VJOURNALs. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class VJournal extends VObject\Component { - - /** - * Returns true or false depending on if the event falls in the specified - * time-range. This is used for filtering purposes. - * - * The rules used to determine if an event falls within the specified - * time-range is based on the CalDAV specification. - * - * @param DateTime $start - * @param DateTime $end - * @return bool - */ - public function isInTimeRange(\DateTime $start, \DateTime $end) { - - $dtstart = isset($this->DTSTART)?$this->DTSTART->getDateTime():null; - if ($dtstart) { - $effectiveEnd = clone $dtstart; - if (!$this->DTSTART->hasTime()) { - $effectiveEnd->modify('+1 day'); - } - - return ($start <= $effectiveEnd && $end > $dtstart); - - } - return false; - - } - - /** - * A simple list of validation rules. - * - * This is simply a list of properties, and how many times they either - * must or must not appear. - * - * Possible values per property: - * * 0 - Must not appear. - * * 1 - Must appear exactly once. - * * + - Must appear at least once. - * * * - Can appear any number of times. - * - * @var array - */ - public function getValidationRules() { - - return array( - 'UID' => 1, - 'DTSTAMP' => 1, - - 'CLASS' => '?', - 'CREATED' => '?', - 'DTSTART' => '?', - 'LAST-MODIFICATION' => '?', - 'ORGANIZER' => '?', - 'RECURRENCE-ID' => '?', - 'SEQUENCE' => '?', - 'STATUS' => '?', - 'SUMMARY' => '?', - 'URL' => '?', - - 'RRULE' => '?', - - 'ATTACH' => '*', - 'ATTENDEE' => '*', - 'CATEGORIES' => '*', - 'COMMENT' => '*', - 'CONTACT' => '*', - 'DESCRIPTION' => '*', - 'EXDATE' => '*', - 'RELATED-TO' => '*', - 'RDATE' => '*', - ); - - } -}
--- a/vendor/sabre/vobject/lib/Component/VTimeZone.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,67 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -/** - * The VTimeZone component - * - * This component adds functionality to a component, specific for VTIMEZONE - * components. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class VTimeZone extends VObject\Component { - - /** - * Returns the PHP DateTimeZone for this VTIMEZONE component. - * - * If we can't accurately determine the timezone, this method will return - * UTC. - * - * @return \DateTimeZone - */ - function getTimeZone() { - - return VObject\TimeZoneUtil::getTimeZone((string)$this->TZID, $this->root); - - } - - /** - * A simple list of validation rules. - * - * This is simply a list of properties, and how many times they either - * must or must not appear. - * - * Possible values per property: - * * 0 - Must not appear. - * * 1 - Must appear exactly once. - * * + - Must appear at least once. - * * * - Can appear any number of times. - * - * @var array - */ - function getValidationRules() { - - return array( - 'TZID' => 1, - - 'LAST-MODIFICATION' => '?', - 'TZURL' => '?', - - // At least 1 STANDARD or DAYLIGHT must appear, or more. But both - // cannot appear in the same VTIMEZONE. - // - // The validator is not specific yet to pick this up, so these - // rules are too loose. - 'STANDARD' => '*', - 'DAYLIGHT' => '*', - ); - - } - -} -
--- a/vendor/sabre/vobject/lib/Component/VTodo.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,176 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -/** - * VTodo component - * - * This component contains some additional functionality specific for VTODOs. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class VTodo extends VObject\Component { - - /** - * Returns true or false depending on if the event falls in the specified - * time-range. This is used for filtering purposes. - * - * The rules used to determine if an event falls within the specified - * time-range is based on the CalDAV specification. - * - * @param DateTime $start - * @param DateTime $end - * @return bool - */ - public function isInTimeRange(\DateTime $start, \DateTime $end) { - - $dtstart = isset($this->DTSTART)?$this->DTSTART->getDateTime():null; - $duration = isset($this->DURATION)?VObject\DateTimeParser::parseDuration($this->DURATION):null; - $due = isset($this->DUE)?$this->DUE->getDateTime():null; - $completed = isset($this->COMPLETED)?$this->COMPLETED->getDateTime():null; - $created = isset($this->CREATED)?$this->CREATED->getDateTime():null; - - if ($dtstart) { - if ($duration) { - $effectiveEnd = clone $dtstart; - $effectiveEnd->add($duration); - return $start <= $effectiveEnd && $end > $dtstart; - } elseif ($due) { - return - ($start < $due || $start <= $dtstart) && - ($end > $dtstart || $end >= $due); - } else { - return $start <= $dtstart && $end > $dtstart; - } - } - if ($due) { - return ($start < $due && $end >= $due); - } - if ($completed && $created) { - return - ($start <= $created || $start <= $completed) && - ($end >= $created || $end >= $completed); - } - if ($completed) { - return ($start <= $completed && $end >= $completed); - } - if ($created) { - return ($end > $created); - } - return true; - - } - - /** - * A simple list of validation rules. - * - * This is simply a list of properties, and how many times they either - * must or must not appear. - * - * Possible values per property: - * * 0 - Must not appear. - * * 1 - Must appear exactly once. - * * + - Must appear at least once. - * * * - Can appear any number of times. - * - * @var array - */ - public function getValidationRules() { - - return array( - 'UID' => 1, - 'DTSTAMP' => 1, - - 'CLASS' => '?', - 'COMPLETED' => '?', - 'CREATED' => '?', - 'DESCRIPTION' => '?', - 'DTSTART' => '?', - 'GEO' => '?', - 'LAST-MODIFICATION' => '?', - 'LOCATION' => '?', - 'ORGANIZER' => '?', - 'PERCENT' => '?', - 'PRIORITY' => '?', - 'RECURRENCE-ID' => '?', - 'SEQUENCE' => '?', - 'STATUS' => '?', - 'SUMMARY' => '?', - 'URL' => '?', - - 'RRULE' => '?', - 'DUE' => '?', - 'DURATION' => '?', - - 'ATTACH' => '*', - 'ATTENDEE' => '*', - 'CATEGORIES' => '*', - 'COMMENT' => '*', - 'CONTACT' => '*', - 'EXDATE' => '*', - 'REQUEST-STATUS' => '*', - 'RELATED-TO' => '*', - 'RESOURCES' => '*', - 'RDATE' => '*', - ); - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * Node::REPAIR - May attempt to automatically repair the problem. - * - * This method returns an array with detected problems. - * Every element has the following properties: - * - * * level - problem level. - * * message - A human-readable string describing the issue. - * * node - A reference to the problematic node. - * - * The level means: - * 1 - The issue was repaired (only happens if REPAIR was turned on) - * 2 - An inconsequential issue - * 3 - A severe issue. - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - $result = parent::validate($options); - if (isset($this->DUE) && isset($this->DTSTART)) { - - $due = $this->DUE; - $dtStart = $this->DTSTART; - - if ($due->getValueType() !== $dtStart->getValueType()) { - - $result[] = array( - 'level' => 3, - 'message' => 'The value type (DATE or DATE-TIME) must be identical for DUE and DTSTART', - 'node' => $due, - ); - - } elseif ($due->getDateTime() < $dtStart->getDateTime()) { - - $result[] = array( - 'level' => 3, - 'message' => 'DUE must occur after DTSTART', - 'node' => $due, - ); - - } - - } - - return $result; - - } - -}
--- a/vendor/sabre/vobject/lib/DateTimeParser.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,428 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use DateTime; -use DateTimeZone; -use DateInterval; -use InvalidArgumentException; -use LogicException; - -/** - * DateTimeParser - * - * This class is responsible for parsing the several different date and time - * formats iCalendar and vCards have. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class DateTimeParser { - - /** - * Parses an iCalendar (rfc5545) formatted datetime and returns a DateTime object - * - * Specifying a reference timezone is optional. It will only be used - * if the non-UTC format is used. The argument is used as a reference, the - * returned DateTime object will still be in the UTC timezone. - * - * @param string $dt - * @param DateTimeZone $tz - * @return DateTime - */ - static public function parseDateTime($dt, DateTimeZone $tz = null) { - - // Format is YYYYMMDD + "T" + hhmmss - $result = preg_match('/^([0-9]{4})([0-1][0-9])([0-3][0-9])T([0-2][0-9])([0-5][0-9])([0-5][0-9])([Z]?)$/',$dt,$matches); - - if (!$result) { - throw new LogicException('The supplied iCalendar datetime value is incorrect: ' . $dt); - } - - if ($matches[7]==='Z' || is_null($tz)) { - $tz = new DateTimeZone('UTC'); - } - $date = new DateTime($matches[1] . '-' . $matches[2] . '-' . $matches[3] . ' ' . $matches[4] . ':' . $matches[5] .':' . $matches[6], $tz); - - // Still resetting the timezone, to normalize everything to UTC - // $date->setTimeZone(new \DateTimeZone('UTC')); - return $date; - - } - - /** - * Parses an iCalendar (rfc5545) formatted date and returns a DateTime object. - * - * @param string $date - * @param DateTimeZone $tz - * @return DateTime - */ - static public function parseDate($date, DateTimeZone $tz = null) { - - // Format is YYYYMMDD - $result = preg_match('/^([0-9]{4})([0-1][0-9])([0-3][0-9])$/',$date,$matches); - - if (!$result) { - throw new LogicException('The supplied iCalendar date value is incorrect: ' . $date); - } - - if (is_null($tz)) { - $tz = new DateTimeZone('UTC'); - } - - $date = new DateTime($matches[1] . '-' . $matches[2] . '-' . $matches[3], $tz); - return $date; - - } - - /** - * Parses an iCalendar (RFC5545) formatted duration value. - * - * This method will either return a DateTimeInterval object, or a string - * suitable for strtotime or DateTime::modify. - * - * @param string $duration - * @param bool $asString - * @return DateInterval|string - */ - static public function parseDuration($duration, $asString = false) { - - $result = preg_match('/^(?P<plusminus>\+|-)?P((?P<week>\d+)W)?((?P<day>\d+)D)?(T((?P<hour>\d+)H)?((?P<minute>\d+)M)?((?P<second>\d+)S)?)?$/', $duration, $matches); - if (!$result) { - throw new LogicException('The supplied iCalendar duration value is incorrect: ' . $duration); - } - - if (!$asString) { - $invert = false; - if ($matches['plusminus']==='-') { - $invert = true; - } - - - $parts = array( - 'week', - 'day', - 'hour', - 'minute', - 'second', - ); - foreach($parts as $part) { - $matches[$part] = isset($matches[$part])&&$matches[$part]?(int)$matches[$part]:0; - } - - - // We need to re-construct the $duration string, because weeks and - // days are not supported by DateInterval in the same string. - $duration = 'P'; - $days = $matches['day']; - if ($matches['week']) { - $days+=$matches['week']*7; - } - if ($days) - $duration.=$days . 'D'; - - if ($matches['minute'] || $matches['second'] || $matches['hour']) { - $duration.='T'; - - if ($matches['hour']) - $duration.=$matches['hour'].'H'; - - if ($matches['minute']) - $duration.=$matches['minute'].'M'; - - if ($matches['second']) - $duration.=$matches['second'].'S'; - - } - - if ($duration==='P') { - $duration = 'PT0S'; - } - $iv = new DateInterval($duration); - if ($invert) $iv->invert = true; - - return $iv; - - } - - - - $parts = array( - 'week', - 'day', - 'hour', - 'minute', - 'second', - ); - - $newDur = ''; - foreach($parts as $part) { - if (isset($matches[$part]) && $matches[$part]) { - $newDur.=' '.$matches[$part] . ' ' . $part . 's'; - } - } - - $newDur = ($matches['plusminus']==='-'?'-':'+') . trim($newDur); - if ($newDur === '+') { - $newDur = '+0 seconds'; - }; - return $newDur; - - } - - /** - * Parses either a Date or DateTime, or Duration value. - * - * @param string $date - * @param DateTimeZone|string $referenceTz - * @return DateTime|DateInterval - */ - static public function parse($date, $referenceTz = null) { - - if ($date[0]==='P' || ($date[0]==='-' && $date[1]==='P')) { - return self::parseDuration($date); - } elseif (strlen($date)===8) { - return self::parseDate($date, $referenceTz); - } else { - return self::parseDateTime($date, $referenceTz); - } - - } - - /** - * This method parses a vCard date and or time value. - * - * This can be used for the DATE, DATE-TIME, TIMESTAMP and - * DATE-AND-OR-TIME value. - * - * This method returns an array, not a DateTime value. - * - * The elements in the array are in the following order: - * year, month, date, hour, minute, second, timezone - * - * Almost any part of the string may be omitted. It's for example legal to - * just specify seconds, leave out the year, etc. - * - * Timezone is either returned as 'Z' or as '+08:00' - * - * For any non-specified values null is returned. - * - * List of date formats that are supported: - * YYYY - * YYYY-MM - * YYYYMMDD - * --MMDD - * ---DD - * - * YYYY-MM-DD - * --MM-DD - * ---DD - * - * List of supported time formats: - * - * HH - * HHMM - * HHMMSS - * -MMSS - * --SS - * - * HH - * HH:MM - * HH:MM:SS - * -MM:SS - * --SS - * - * A full basic-format date-time string looks like : - * 20130603T133901 - * - * A full extended-format date-time string looks like : - * 2013-06-03T13:39:01 - * - * Times may be postfixed by a timezone offset. This can be either 'Z' for - * UTC, or a string like -0500 or +1100. - * - * @param string $date - * @return array - */ - static public function parseVCardDateTime($date) { - - $regex = '/^ - (?: # date part - (?: - (?: (?P<year> [0-9]{4}) (?: -)?| --) - (?P<month> [0-9]{2})? - |---) - (?P<date> [0-9]{2})? - )? - (?:T # time part - (?P<hour> [0-9]{2} | -) - (?P<minute> [0-9]{2} | -)? - (?P<second> [0-9]{2})? - - (?P<timezone> # timezone offset - - Z | (?: \+|-)(?: [0-9]{4}) - - )? - - )? - $/x'; - - - if (!preg_match($regex, $date, $matches)) { - - // Attempting to parse the extended format. - $regex = '/^ - (?: # date part - (?: (?P<year> [0-9]{4}) - | -- ) - (?P<month> [0-9]{2}) - - (?P<date> [0-9]{2}) - )? - (?:T # time part - - (?: (?P<hour> [0-9]{2}) : | -) - (?: (?P<minute> [0-9]{2}) : | -)? - (?P<second> [0-9]{2})? - - (?P<timezone> # timezone offset - - Z | (?: \+|-)(?: [0-9]{2}:[0-9]{2}) - - )? - - )? - $/x'; - - if (!preg_match($regex, $date, $matches)) { - throw new InvalidArgumentException('Invalid vCard date-time string: ' . $date); - } - - } - $parts = array( - 'year', - 'month', - 'date', - 'hour', - 'minute', - 'second', - 'timezone' - ); - - $result = array(); - foreach($parts as $part) { - - if (empty($matches[$part])) { - $result[$part] = null; - } elseif ($matches[$part] === '-' || $matches[$part] === '--') { - $result[$part] = null; - } else { - $result[$part] = $matches[$part]; - } - - } - - return $result; - - } - - /** - * This method parses a vCard TIME value. - * - * This method returns an array, not a DateTime value. - * - * The elements in the array are in the following order: - * hour, minute, second, timezone - * - * Almost any part of the string may be omitted. It's for example legal to - * just specify seconds, leave out the hour etc. - * - * Timezone is either returned as 'Z' or as '+08:00' - * - * For any non-specified values null is returned. - * - * List of supported time formats: - * - * HH - * HHMM - * HHMMSS - * -MMSS - * --SS - * - * HH - * HH:MM - * HH:MM:SS - * -MM:SS - * --SS - * - * A full basic-format time string looks like : - * 133901 - * - * A full extended-format time string looks like : - * 13:39:01 - * - * Times may be postfixed by a timezone offset. This can be either 'Z' for - * UTC, or a string like -0500 or +11:00. - * - * @param string $date - * @return array - */ - static public function parseVCardTime($date) { - - $regex = '/^ - (?P<hour> [0-9]{2} | -) - (?P<minute> [0-9]{2} | -)? - (?P<second> [0-9]{2})? - - (?P<timezone> # timezone offset - - Z | (?: \+|-)(?: [0-9]{4}) - - )? - $/x'; - - - if (!preg_match($regex, $date, $matches)) { - - // Attempting to parse the extended format. - $regex = '/^ - (?: (?P<hour> [0-9]{2}) : | -) - (?: (?P<minute> [0-9]{2}) : | -)? - (?P<second> [0-9]{2})? - - (?P<timezone> # timezone offset - - Z | (?: \+|-)(?: [0-9]{2}:[0-9]{2}) - - )? - $/x'; - - if (!preg_match($regex, $date, $matches)) { - throw new InvalidArgumentException('Invalid vCard time string: ' . $date); - } - - } - $parts = array( - 'hour', - 'minute', - 'second', - 'timezone' - ); - - $result = array(); - foreach($parts as $part) { - - if (empty($matches[$part])) { - $result[$part] = null; - } elseif ($matches[$part] === '-') { - $result[$part] = null; - } else { - $result[$part] = $matches[$part]; - } - - } - - return $result; - - } -}
--- a/vendor/sabre/vobject/lib/Document.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,261 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Document - * - * A document is just like a component, except that it's also the top level - * element. - * - * Both a VCALENDAR and a VCARD are considered documents. - * - * This class also provides a registry for document types. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -abstract class Document extends Component { - - /** - * Unknown document type - */ - const UNKNOWN = 1; - - /** - * vCalendar 1.0 - */ - const VCALENDAR10 = 2; - - /** - * iCalendar 2.0 - */ - const ICALENDAR20 = 3; - - /** - * vCard 2.1 - */ - const VCARD21 = 4; - - /** - * vCard 3.0 - */ - const VCARD30 = 5; - - /** - * vCard 4.0 - */ - const VCARD40 = 6; - - /** - * The default name for this component. - * - * This should be 'VCALENDAR' or 'VCARD'. - * - * @var string - */ - static public $defaultName; - - /** - * List of properties, and which classes they map to. - * - * @var array - */ - static public $propertyMap = array(); - - /** - * List of components, along with which classes they map to. - * - * @var array - */ - static public $componentMap = array(); - - /** - * List of value-types, and which classes they map to. - * - * @var array - */ - static public $valueMap = array(); - - /** - * Creates a new document. - * - * We're changing the default behavior slightly here. First, we don't want - * to have to specify a name (we already know it), and we want to allow - * children to be specified in the first argument. - * - * But, the default behavior also works. - * - * So the two sigs: - * - * new Document(array $children = array(), $defaults = true); - * new Document(string $name, array $children = array(), $defaults = true) - * - * @return void - */ - public function __construct() { - - $args = func_get_args(); - if (count($args)===0 || is_array($args[0])) { - array_unshift($args, $this, static::$defaultName); - call_user_func_array(array('parent', '__construct'), $args); - } else { - array_unshift($args, $this); - call_user_func_array(array('parent', '__construct'), $args); - } - - } - - /** - * Returns the current document type. - * - * @return void - */ - public function getDocumentType() { - - return self::UNKNOWN; - - } - - /** - * Creates a new component or property. - * - * If it's a known component, we will automatically call createComponent. - * otherwise, we'll assume it's a property and call createProperty instead. - * - * @param string $name - * @param string $arg1,... Unlimited number of args - * @return mixed - */ - public function create($name) { - - if (isset(static::$componentMap[strtoupper($name)])) { - - return call_user_func_array(array($this,'createComponent'), func_get_args()); - - } else { - - return call_user_func_array(array($this,'createProperty'), func_get_args()); - - } - - } - - /** - * Creates a new component - * - * This method automatically searches for the correct component class, based - * on its name. - * - * You can specify the children either in key=>value syntax, in which case - * properties will automatically be created, or you can just pass a list of - * Component and Property object. - * - * By default, a set of sensible values will be added to the component. For - * an iCalendar object, this may be something like CALSCALE:GREGORIAN. To - * ensure that this does not happen, set $defaults to false. - * - * @param string $name - * @param array $children - * @param bool $defaults - * @return Component - */ - public function createComponent($name, array $children = null, $defaults = true) { - - $name = strtoupper($name); - $class = 'Sabre\\VObject\\Component'; - - if (isset(static::$componentMap[$name])) { - $class=static::$componentMap[$name]; - } - if (is_null($children)) $children = array(); - return new $class($this, $name, $children, $defaults); - - } - - /** - * Factory method for creating new properties - * - * This method automatically searches for the correct property class, based - * on its name. - * - * You can specify the parameters either in key=>value syntax, in which case - * parameters will automatically be created, or you can just pass a list of - * Parameter objects. - * - * @param string $name - * @param mixed $value - * @param array $parameters - * @param string $valueType Force a specific valuetype, such as URI or TEXT - * @return Property - */ - public function createProperty($name, $value = null, array $parameters = null, $valueType = null) { - - // If there's a . in the name, it means it's prefixed by a groupname. - if (($i=strpos($name,'.'))!==false) { - $group = substr($name, 0, $i); - $name = strtoupper(substr($name, $i+1)); - } else { - $name = strtoupper($name); - $group = null; - } - - $class = null; - - if ($valueType) { - // The valueType argument comes first to figure out the correct - // class. - $class = $this->getClassNameForPropertyValue($valueType); - } - - if (is_null($class) && isset($parameters['VALUE'])) { - // If a VALUE parameter is supplied, we should use that. - $class = $this->getClassNameForPropertyValue($parameters['VALUE']); - } - if (is_null($class)) { - $class = $this->getClassNameForPropertyName($name); - } - if (is_null($parameters)) $parameters = array(); - - return new $class($this, $name, $value, $parameters, $group); - - } - - /** - * This method returns a full class-name for a value parameter. - * - * For instance, DTSTART may have VALUE=DATE. In that case we will look in - * our valueMap table and return the appropriate class name. - * - * This method returns null if we don't have a specialized class. - * - * @param string $valueParam - * @return void - */ - public function getClassNameForPropertyValue($valueParam) { - - $valueParam = strtoupper($valueParam); - if (isset(static::$valueMap[$valueParam])) { - return static::$valueMap[$valueParam]; - } - - } - - /** - * Returns the default class for a property name. - * - * @param string $propertyName - * @return string - */ - public function getClassNameForPropertyName($propertyName) { - - if (isset(static::$propertyMap[$propertyName])) { - return static::$propertyMap[$propertyName]; - } else { - return 'Sabre\\VObject\\Property\\Unknown'; - } - - } - -}
--- a/vendor/sabre/vobject/lib/ElementList.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,172 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * VObject ElementList - * - * This class represents a list of elements. Lists are the result of queries, - * such as doing $vcalendar->vevent where there's multiple VEVENT objects. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class ElementList implements \Iterator, \Countable, \ArrayAccess { - - /** - * Inner elements - * - * @var array - */ - protected $elements = array(); - - /** - * Creates the element list. - * - * @param array $elements - */ - public function __construct(array $elements) { - - $this->elements = $elements; - - } - - /* {{{ Iterator interface */ - - /** - * Current position - * - * @var int - */ - private $key = 0; - - /** - * Returns current item in iteration - * - * @return Element - */ - public function current() { - - return $this->elements[$this->key]; - - } - - /** - * To the next item in the iterator - * - * @return void - */ - public function next() { - - $this->key++; - - } - - /** - * Returns the current iterator key - * - * @return int - */ - public function key() { - - return $this->key; - - } - - /** - * Returns true if the current position in the iterator is a valid one - * - * @return bool - */ - public function valid() { - - return isset($this->elements[$this->key]); - - } - - /** - * Rewinds the iterator - * - * @return void - */ - public function rewind() { - - $this->key = 0; - - } - - /* }}} */ - - /* {{{ Countable interface */ - - /** - * Returns the number of elements - * - * @return int - */ - public function count() { - - return count($this->elements); - - } - - /* }}} */ - - /* {{{ ArrayAccess Interface */ - - - /** - * Checks if an item exists through ArrayAccess. - * - * @param int $offset - * @return bool - */ - public function offsetExists($offset) { - - return isset($this->elements[$offset]); - - } - - /** - * Gets an item through ArrayAccess. - * - * @param int $offset - * @return mixed - */ - public function offsetGet($offset) { - - return $this->elements[$offset]; - - } - - /** - * Sets an item through ArrayAccess. - * - * @param int $offset - * @param mixed $value - * @return void - */ - public function offsetSet($offset, $value) { - - throw new \LogicException('You can not add new objects to an ElementList'); - - } - - /** - * Sets an item through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @return void - */ - public function offsetUnset($offset) { - - throw new \LogicException('You can not remove objects from an ElementList'); - - } - - /* }}} */ - -}
--- a/vendor/sabre/vobject/lib/EofException.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,15 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Exception thrown by parser when the end of the stream has been reached, - * before this was expected. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class EofException extends ParseException { - -}
--- a/vendor/sabre/vobject/lib/FreeBusyGenerator.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,355 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use DateTimeZone; -use Sabre\VObject\Component\VCalendar; -use Sabre\VObject\Recur\EventIterator; - -/** - * This class helps with generating FREEBUSY reports based on existing sets of - * objects. - * - * It only looks at VEVENT and VFREEBUSY objects from the sourcedata, and - * generates a single VFREEBUSY object. - * - * VFREEBUSY components are described in RFC5545, The rules for what should - * go in a single freebusy report is taken from RFC4791, section 7.10. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class FreeBusyGenerator { - - /** - * Input objects - * - * @var array - */ - protected $objects; - - /** - * Start of range - * - * @var DateTime|null - */ - protected $start; - - /** - * End of range - * - * @var DateTime|null - */ - protected $end; - - /** - * VCALENDAR object - * - * @var Component - */ - protected $baseObject; - - /** - * Reference timezone. - * - * When we are calculating busy times, and we come across so-called - * floating times (times without a timezone), we use the reference timezone - * instead. - * - * This is also used for all-day events. - * - * This defaults to UTC. - * - * @var DateTimeZone - */ - protected $timeZone; - - /** - * Creates the generator. - * - * Check the setTimeRange and setObjects methods for details about the - * arguments. - * - * @param DateTime $start - * @param DateTime $end - * @param mixed $objects - * @param DateTimeZone $timeZone - * @return void - */ - public function __construct(\DateTime $start = null, \DateTime $end = null, $objects = null, DateTimeZone $timeZone = null) { - - if ($start && $end) { - $this->setTimeRange($start, $end); - } - - if ($objects) { - $this->setObjects($objects); - } - if (is_null($timeZone)) { - $timeZone = new DateTimeZone('UTC'); - } - $this->setTimeZone($timeZone); - - } - - /** - * Sets the VCALENDAR object. - * - * If this is set, it will not be generated for you. You are responsible - * for setting things like the METHOD, CALSCALE, VERSION, etc.. - * - * The VFREEBUSY object will be automatically added though. - * - * @param Component $vcalendar - * @return void - */ - public function setBaseObject(Component $vcalendar) { - - $this->baseObject = $vcalendar; - - } - - /** - * Sets the input objects - * - * You must either specify a valendar object as a strong, or as the parse - * Component. - * It's also possible to specify multiple objects as an array. - * - * @param mixed $objects - * @return void - */ - public function setObjects($objects) { - - if (!is_array($objects)) { - $objects = array($objects); - } - - $this->objects = array(); - foreach($objects as $object) { - - if (is_string($object)) { - $this->objects[] = Reader::read($object); - } elseif ($object instanceof Component) { - $this->objects[] = $object; - } else { - throw new \InvalidArgumentException('You can only pass strings or \\Sabre\\VObject\\Component arguments to setObjects'); - } - - } - - } - - /** - * Sets the time range - * - * Any freebusy object falling outside of this time range will be ignored. - * - * @param DateTime $start - * @param DateTime $end - * @return void - */ - public function setTimeRange(\DateTime $start = null, \DateTime $end = null) { - - $this->start = $start; - $this->end = $end; - - } - - /** - * Sets the reference timezone for floating times. - * - * @param DateTimeZone $timeZone - * @return void - */ - public function setTimeZone(DateTimeZone $timeZone) { - - $this->timeZone = $timeZone; - - } - - /** - * Parses the input data and returns a correct VFREEBUSY object, wrapped in - * a VCALENDAR. - * - * @return Component - */ - public function getResult() { - - $busyTimes = array(); - - foreach($this->objects as $object) { - - foreach($object->getBaseComponents() as $component) { - - switch($component->name) { - - case 'VEVENT' : - - $FBTYPE = 'BUSY'; - if (isset($component->TRANSP) && (strtoupper($component->TRANSP) === 'TRANSPARENT')) { - break; - } - if (isset($component->STATUS)) { - $status = strtoupper($component->STATUS); - if ($status==='CANCELLED') { - break; - } - if ($status==='TENTATIVE') { - $FBTYPE = 'BUSY-TENTATIVE'; - } - } - - $times = array(); - - if ($component->RRULE) { - - $iterator = new EventIterator($object, (string)$component->uid, $this->timeZone); - if ($this->start) { - $iterator->fastForward($this->start); - } - - $maxRecurrences = 200; - - while($iterator->valid() && --$maxRecurrences) { - - $startTime = $iterator->getDTStart(); - if ($this->end && $startTime > $this->end) { - break; - } - $times[] = array( - $iterator->getDTStart(), - $iterator->getDTEnd(), - ); - - $iterator->next(); - - } - - } else { - - $startTime = $component->DTSTART->getDateTime($this->timeZone); - if ($this->end && $startTime > $this->end) { - break; - } - $endTime = null; - if (isset($component->DTEND)) { - $endTime = $component->DTEND->getDateTime($this->timeZone); - } elseif (isset($component->DURATION)) { - $duration = DateTimeParser::parseDuration((string)$component->DURATION); - $endTime = clone $startTime; - $endTime->add($duration); - } elseif (!$component->DTSTART->hasTime()) { - $endTime = clone $startTime; - $endTime->modify('+1 day'); - } else { - // The event had no duration (0 seconds) - break; - } - - $times[] = array($startTime, $endTime); - - } - - foreach($times as $time) { - - if ($this->end && $time[0] > $this->end) break; - if ($this->start && $time[1] < $this->start) break; - - $busyTimes[] = array( - $time[0], - $time[1], - $FBTYPE, - ); - } - break; - - case 'VFREEBUSY' : - foreach($component->FREEBUSY as $freebusy) { - - $fbType = isset($freebusy['FBTYPE'])?strtoupper($freebusy['FBTYPE']):'BUSY'; - - // Skipping intervals marked as 'free' - if ($fbType==='FREE') - continue; - - $values = explode(',', $freebusy); - foreach($values as $value) { - list($startTime, $endTime) = explode('/', $value); - $startTime = DateTimeParser::parseDateTime($startTime); - - if (substr($endTime,0,1)==='P' || substr($endTime,0,2)==='-P') { - $duration = DateTimeParser::parseDuration($endTime); - $endTime = clone $startTime; - $endTime->add($duration); - } else { - $endTime = DateTimeParser::parseDateTime($endTime); - } - - if($this->start && $this->start > $endTime) continue; - if($this->end && $this->end < $startTime) continue; - $busyTimes[] = array( - $startTime, - $endTime, - $fbType - ); - - } - - - } - break; - - - - } - - - } - - } - - if ($this->baseObject) { - $calendar = $this->baseObject; - } else { - $calendar = new VCalendar(); - } - - $vfreebusy = $calendar->createComponent('VFREEBUSY'); - $calendar->add($vfreebusy); - - if ($this->start) { - $dtstart = $calendar->createProperty('DTSTART'); - $dtstart->setDateTime($this->start); - $vfreebusy->add($dtstart); - } - if ($this->end) { - $dtend = $calendar->createProperty('DTEND'); - $dtend->setDateTime($this->end); - $vfreebusy->add($dtend); - } - $dtstamp = $calendar->createProperty('DTSTAMP'); - $dtstamp->setDateTime(new \DateTime('now', new \DateTimeZone('UTC'))); - $vfreebusy->add($dtstamp); - - foreach($busyTimes as $busyTime) { - - $busyTime[0]->setTimeZone(new \DateTimeZone('UTC')); - $busyTime[1]->setTimeZone(new \DateTimeZone('UTC')); - - $prop = $calendar->createProperty( - 'FREEBUSY', - $busyTime[0]->format('Ymd\\THis\\Z') . '/' . $busyTime[1]->format('Ymd\\THis\\Z') - ); - $prop['FBTYPE'] = $busyTime[2]; - $vfreebusy->add($prop); - - } - - return $calendar; - - } - -} -
--- a/vendor/sabre/vobject/lib/ITip/Broker.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,942 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -use Sabre\VObject\Component\VCalendar; -use Sabre\VObject\DateTimeParser; -use Sabre\VObject\Reader; -use Sabre\VObject\Recur\EventIterator; - -/** - * The ITip\Broker class is a utility class that helps with processing - * so-called iTip messages. - * - * iTip is defined in rfc5546, stands for iCalendar Transport-Independent - * Interoperability Protocol, and describes the underlying mechanism for - * using iCalendar for scheduling for for example through email (also known as - * IMip) and CalDAV Scheduling. - * - * This class helps by: - * - * 1. Creating individual invites based on an iCalendar event for each - * attendee. - * 2. Generating invite updates based on an iCalendar update. This may result - * in new invites, updates and cancellations for attendees, if that list - * changed. - * 3. On the receiving end, it can create a local iCalendar event based on - * a received invite. - * 4. It can also process an invite update on a local event, ensuring that any - * overridden properties from attendees are retained. - * 5. It can create a accepted or declined iTip reply based on an invite. - * 6. It can process a reply from an invite and update an events attendee - * status based on a reply. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Broker { - - /** - * This setting determines whether the rules for the SCHEDULE-AGENT - * parameter should be followed. - * - * This is a parameter defined on ATTENDEE properties, introduced by RFC - * 6638. This parameter allows a caldav client to tell the server 'Don't do - * any scheduling operations'. - * - * If this setting is turned on, any attendees with SCHEDULE-AGENT set to - * CLIENT will be ignored. This is the desired behavior for a CalDAV - * server, but if you're writing an iTip application that doesn't deal with - * CalDAV, you may want to ignore this parameter. - * - * @var bool - */ - public $scheduleAgentServerRules = true; - - /** - * The broker will try during 'parseEvent' figure out whether the change - * was significant. - * - * It uses a few different ways to do this. One of these ways is seeing if - * certain properties changed values. This list of specified here. - * - * This list is taken from: - * * http://tools.ietf.org/html/rfc5546#section-2.1.4 - * - * @var string[] - */ - public $significantChangeProperties = array( - 'DTSTART', - 'DTEND', - 'DURATION', - 'DUE', - 'RRULE', - 'RDATE', - 'EXDATE', - 'STATUS', - ); - - /** - * This method is used to process an incoming itip message. - * - * Examples: - * - * 1. A user is an attendee to an event. The organizer sends an updated - * meeting using a new iTip message with METHOD:REQUEST. This function - * will process the message and update the attendee's event accordingly. - * - * 2. The organizer cancelled the event using METHOD:CANCEL. We will update - * the users event to state STATUS:CANCELLED. - * - * 3. An attendee sent a reply to an invite using METHOD:REPLY. We can - * update the organizers event to update the ATTENDEE with its correct - * PARTSTAT. - * - * The $existingObject is updated in-place. If there is no existing object - * (because it's a new invite for example) a new object will be created. - * - * If an existing object does not exist, and the method was CANCEL or - * REPLY, the message effectively gets ignored, and no 'existingObject' - * will be created. - * - * The updated $existingObject is also returned from this function. - * - * If the iTip message was not supported, we will always return false. - * - * @param Message $itipMessage - * @param VCalendar $existingObject - * @return VCalendar|null - */ - public function processMessage(Message $itipMessage, VCalendar $existingObject = null) { - - // We only support events at the moment. - if ($itipMessage->component !== 'VEVENT') { - return false; - } - - switch($itipMessage->method) { - - case 'REQUEST' : - return $this->processMessageRequest($itipMessage, $existingObject); - - case 'CANCEL' : - return $this->processMessageCancel($itipMessage, $existingObject); - - case 'REPLY' : - return $this->processMessageReply($itipMessage, $existingObject); - - default : - // Unsupported iTip message - return null; - - } - - return $existingObject; - - } - - /** - * This function parses a VCALENDAR object and figure out if any messages - * need to be sent. - * - * A VCALENDAR object will be created from the perspective of either an - * attendee, or an organizer. You must pass a string identifying the - * current user, so we can figure out who in the list of attendees or the - * organizer we are sending this message on behalf of. - * - * It's possible to specify the current user as an array, in case the user - * has more than one identifying href (such as multiple emails). - * - * It $oldCalendar is specified, it is assumed that the operation is - * updating an existing event, which means that we need to look at the - * differences between events, and potentially send old attendees - * cancellations, and current attendees updates. - * - * If $calendar is null, but $oldCalendar is specified, we treat the - * operation as if the user has deleted an event. If the user was an - * organizer, this means that we need to send cancellation notices to - * people. If the user was an attendee, we need to make sure that the - * organizer gets the 'declined' message. - * - * @param VCalendar|string $calendar - * @param string|array $userHref - * @param VCalendar|string $oldCalendar - * @return array - */ - public function parseEvent($calendar = null, $userHref, $oldCalendar = null) { - - if ($oldCalendar) { - if (is_string($oldCalendar)) { - $oldCalendar = Reader::read($oldCalendar); - } - if (!isset($oldCalendar->VEVENT)) { - // We only support events at the moment - return array(); - } - - $oldEventInfo = $this->parseEventInfo($oldCalendar); - } else { - $oldEventInfo = array( - 'organizer' => null, - 'significantChangeHash' => '', - 'attendees' => array(), - ); - } - - $userHref = (array)$userHref; - - if (!is_null($calendar)) { - - if (is_string($calendar)) { - $calendar = Reader::read($calendar); - } - if (!isset($calendar->VEVENT)) { - // We only support events at the moment - return array(); - } - $eventInfo = $this->parseEventInfo($calendar); - if (!$eventInfo['attendees'] && !$oldEventInfo['attendees']) { - // If there were no attendees on either side of the equation, - // we don't need to do anything. - return array(); - } - if (!$eventInfo['organizer'] && !$oldEventInfo['organizer']) { - // There was no organizer before or after the change. - return array(); - } - - $baseCalendar = $calendar; - - // If the new object didn't have an organizer, the organizer - // changed the object from a scheduling object to a non-scheduling - // object. We just copy the info from the old object. - if (!$eventInfo['organizer'] && $oldEventInfo['organizer']) { - $eventInfo['organizer'] = $oldEventInfo['organizer']; - $eventInfo['organizerName'] = $oldEventInfo['organizerName']; - } - - } else { - // The calendar object got deleted, we need to process this as a - // cancellation / decline. - if (!$oldCalendar) { - // No old and no new calendar, there's no thing to do. - return array(); - } - - $eventInfo = $oldEventInfo; - - if (in_array($eventInfo['organizer'], $userHref)) { - // This is an organizer deleting the event. - $eventInfo['attendees'] = array(); - // Increasing the sequence, but only if the organizer deleted - // the event. - $eventInfo['sequence']++; - } else { - // This is an attendee deleting the event. - foreach($eventInfo['attendees'] as $key=>$attendee) { - if (in_array($attendee['href'], $userHref)) { - $eventInfo['attendees'][$key]['instances'] = array('master' => - array('id'=>'master', 'partstat' => 'DECLINED') - ); - } - } - } - $baseCalendar = $oldCalendar; - - } - - if (in_array($eventInfo['organizer'], $userHref)) { - return $this->parseEventForOrganizer($baseCalendar, $eventInfo, $oldEventInfo); - } elseif ($oldCalendar) { - // We need to figure out if the user is an attendee, but we're only - // doing so if there's an oldCalendar, because we only want to - // process updates, not creation of new events. - foreach($eventInfo['attendees'] as $attendee) { - if (in_array($attendee['href'], $userHref)) { - return $this->parseEventForAttendee($baseCalendar, $eventInfo, $oldEventInfo, $attendee['href']); - } - } - } - return array(); - - } - - /** - * Processes incoming REQUEST messages. - * - * This is message from an organizer, and is either a new event - * invite, or an update to an existing one. - * - * - * @param Message $itipMessage - * @param VCalendar $existingObject - * @return VCalendar|null - */ - protected function processMessageRequest(Message $itipMessage, VCalendar $existingObject = null) { - - if (!$existingObject) { - // This is a new invite, and we're just going to copy over - // all the components from the invite. - $existingObject = new VCalendar(); - foreach($itipMessage->message->getComponents() as $component) { - $existingObject->add(clone $component); - } - } else { - // We need to update an existing object with all the new - // information. We can just remove all existing components - // and create new ones. - foreach($existingObject->getComponents() as $component) { - $existingObject->remove($component); - } - foreach($itipMessage->message->getComponents() as $component) { - $existingObject->add(clone $component); - } - } - return $existingObject; - - } - - /** - * Processes incoming CANCEL messages. - * - * This is a message from an organizer, and means that either an - * attendee got removed from an event, or an event got cancelled - * altogether. - * - * @param Message $itipMessage - * @param VCalendar $existingObject - * @return VCalendar|null - */ - protected function processMessageCancel(Message $itipMessage, VCalendar $existingObject = null) { - - if (!$existingObject) { - // The event didn't exist in the first place, so we're just - // ignoring this message. - } else { - foreach($existingObject->VEVENT as $vevent) { - $vevent->STATUS = 'CANCELLED'; - $vevent->SEQUENCE = $itipMessage->sequence; - } - } - return $existingObject; - - } - - /** - * Processes incoming REPLY messages. - * - * The message is a reply. This is for example an attendee telling - * an organizer he accepted the invite, or declined it. - * - * @param Message $itipMessage - * @param VCalendar $existingObject - * @return VCalendar|null - */ - protected function processMessageReply(Message $itipMessage, VCalendar $existingObject = null) { - - // A reply can only be processed based on an existing object. - // If the object is not available, the reply is ignored. - if (!$existingObject) { - return null; - } - $instances = array(); - $requestStatus = '2.0'; - - // Finding all the instances the attendee replied to. - foreach($itipMessage->message->VEVENT as $vevent) { - $recurId = isset($vevent->{'RECURRENCE-ID'})?$vevent->{'RECURRENCE-ID'}->getValue():'master'; - $attendee = $vevent->ATTENDEE; - $instances[$recurId] = $attendee['PARTSTAT']->getValue(); - if (isset($vevent->{'REQUEST-STATUS'})) { - $requestStatus = $vevent->{'REQUEST-STATUS'}->getValue(); - list($requestStatus) = explode(';', $requestStatus); - } - } - - // Now we need to loop through the original organizer event, to find - // all the instances where we have a reply for. - $masterObject = null; - foreach($existingObject->VEVENT as $vevent) { - $recurId = isset($vevent->{'RECURRENCE-ID'})?$vevent->{'RECURRENCE-ID'}->getValue():'master'; - if ($recurId==='master') { - $masterObject = $vevent; - } - if (isset($instances[$recurId])) { - $attendeeFound = false; - if (isset($vevent->ATTENDEE)) { - foreach($vevent->ATTENDEE as $attendee) { - if ($attendee->getValue() === $itipMessage->sender) { - $attendeeFound = true; - $attendee['PARTSTAT'] = $instances[$recurId]; - $attendee['SCHEDULE-STATUS'] = $requestStatus; - // Un-setting the RSVP status, because we now know - // that the attende already replied. - unset($attendee['RSVP']); - break; - } - } - } - if (!$attendeeFound) { - // Adding a new attendee. The iTip documentation calls this - // a party crasher. - $attendee = $vevent->add('ATTENDEE', $itipMessage->sender, array( - 'PARTSTAT' => $instances[$recurId] - )); - if ($itipMessage->senderName) $attendee['CN'] = $itipMessage->senderName; - } - unset($instances[$recurId]); - } - } - - if(!$masterObject) { - // No master object, we can't add new instances. - return null; - } - // If we got replies to instances that did not exist in the - // original list, it means that new exceptions must be created. - foreach($instances as $recurId=>$partstat) { - - $recurrenceIterator = new EventIterator($existingObject, $itipMessage->uid); - $found = false; - $iterations = 1000; - do { - - $newObject = $recurrenceIterator->getEventObject(); - $recurrenceIterator->next(); - - if (isset($newObject->{'RECURRENCE-ID'}) && $newObject->{'RECURRENCE-ID'}->getValue()===$recurId) { - $found = true; - } - $iterations--; - - } while($recurrenceIterator->valid() && !$found && $iterations); - - // Invalid recurrence id. Skipping this object. - if (!$found) continue; - - unset( - $newObject->RRULE, - $newObject->EXDATE, - $newObject->RDATE - ); - $attendeeFound = false; - if (isset($newObject->ATTENDEE)) { - foreach($newObject->ATTENDEE as $attendee) { - if ($attendee->getValue() === $itipMessage->sender) { - $attendeeFound = true; - $attendee['PARTSTAT'] = $partstat; - break; - } - } - } - if (!$attendeeFound) { - // Adding a new attendee - $attendee = $newObject->add('ATTENDEE', $itipMessage->sender, array( - 'PARTSTAT' => $partstat - )); - if ($itipMessage->senderName) { - $attendee['CN'] = $itipMessage->senderName; - } - } - $existingObject->add($newObject); - - } - return $existingObject; - - } - - /** - * This method is used in cases where an event got updated, and we - * potentially need to send emails to attendees to let them know of updates - * in the events. - * - * We will detect which attendees got added, which got removed and create - * specific messages for these situations. - * - * @param VCalendar $calendar - * @param array $eventInfo - * @param array $oldEventInfo - * @return array - */ - protected function parseEventForOrganizer(VCalendar $calendar, array $eventInfo, array $oldEventInfo) { - - // Merging attendee lists. - $attendees = array(); - foreach($oldEventInfo['attendees'] as $attendee) { - $attendees[$attendee['href']] = array( - 'href' => $attendee['href'], - 'oldInstances' => $attendee['instances'], - 'newInstances' => array(), - 'name' => $attendee['name'], - 'forceSend' => null, - ); - } - foreach($eventInfo['attendees'] as $attendee) { - if (isset($attendees[$attendee['href']])) { - $attendees[$attendee['href']]['name'] = $attendee['name']; - $attendees[$attendee['href']]['newInstances'] = $attendee['instances']; - $attendees[$attendee['href']]['forceSend'] = $attendee['forceSend']; - } else { - $attendees[$attendee['href']] = array( - 'href' => $attendee['href'], - 'oldInstances' => array(), - 'newInstances' => $attendee['instances'], - 'name' => $attendee['name'], - 'forceSend' => $attendee['forceSend'], - ); - } - } - - $messages = array(); - - foreach($attendees as $attendee) { - - // An organizer can also be an attendee. We should not generate any - // messages for those. - if ($attendee['href']===$eventInfo['organizer']) { - continue; - } - - $message = new Message(); - $message->uid = $eventInfo['uid']; - $message->component = 'VEVENT'; - $message->sequence = $eventInfo['sequence']; - $message->sender = $eventInfo['organizer']; - $message->senderName = $eventInfo['organizerName']; - $message->recipient = $attendee['href']; - $message->recipientName = $attendee['name']; - - if (!$attendee['newInstances']) { - - // If there are no instances the attendee is a part of, it - // means the attendee was removed and we need to send him a - // CANCEL. - $message->method = 'CANCEL'; - - // Creating the new iCalendar body. - $icalMsg = new VCalendar(); - $icalMsg->METHOD = $message->method; - $event = $icalMsg->add('VEVENT', array( - 'UID' => $message->uid, - 'SEQUENCE' => $message->sequence, - )); - if (isset($calendar->VEVENT->SUMMARY)) { - $event->add('SUMMARY', $calendar->VEVENT->SUMMARY->getValue()); - } - $event->add(clone $calendar->VEVENT->DTSTART); - $org = $event->add('ORGANIZER', $eventInfo['organizer']); - if ($eventInfo['organizerName']) $org['CN'] = $eventInfo['organizerName']; - $event->add('ATTENDEE', $attendee['href'], array( - 'CN' => $attendee['name'], - )); - $message->significantChange = true; - - } else { - - // The attendee gets the updated event body - $message->method = 'REQUEST'; - - // Creating the new iCalendar body. - $icalMsg = new VCalendar(); - $icalMsg->METHOD = $message->method; - - foreach($calendar->select('VTIMEZONE') as $timezone) { - $icalMsg->add(clone $timezone); - } - - // We need to find out that this change is significant. If it's - // not, systems may opt to not send messages. - // - // We do this based on the 'significantChangeHash' which is - // some value that changes if there's a certain set of - // properties changed in the event, or simply if there's a - // difference in instances that the attendee is invited to. - - $message->significantChange = - $attendee['forceSend'] === 'REQUEST' || - array_keys($attendee['oldInstances']) != array_keys($attendee['newInstances']) || - $oldEventInfo['significantChangeHash']!==$eventInfo['significantChangeHash']; - - foreach($attendee['newInstances'] as $instanceId => $instanceInfo) { - - $currentEvent = clone $eventInfo['instances'][$instanceId]; - if ($instanceId === 'master') { - - // We need to find a list of events that the attendee - // is not a part of to add to the list of exceptions. - $exceptions = array(); - foreach($eventInfo['instances'] as $instanceId=>$vevent) { - if (!isset($attendee['newInstances'][$instanceId])) { - $exceptions[] = $instanceId; - } - } - - // If there were exceptions, we need to add it to an - // existing EXDATE property, if it exists. - if ($exceptions) { - if (isset($currentEvent->EXDATE)) { - $currentEvent->EXDATE->setParts(array_merge( - $currentEvent->EXDATE->getParts(), - $exceptions - )); - } else { - $currentEvent->EXDATE = $exceptions; - } - } - - // Cleaning up any scheduling information that - // shouldn't be sent along. - unset($currentEvent->ORGANIZER['SCHEDULE-FORCE-SEND']); - unset($currentEvent->ORGANIZER['SCHEDULE-STATUS']); - - foreach($currentEvent->ATTENDEE as $attendee) { - unset($attendee['SCHEDULE-FORCE-SEND']); - unset($attendee['SCHEDULE-STATUS']); - - // We're adding PARTSTAT=NEEDS-ACTION to ensure that - // iOS shows an "Inbox Item" - if (!isset($attendee['PARTSTAT'])) { - $attendee['PARTSTAT'] = 'NEEDS-ACTION'; - } - - } - - } - - $icalMsg->add($currentEvent); - - } - - } - - $message->message = $icalMsg; - $messages[] = $message; - - } - - return $messages; - - } - - /** - * Parse an event update for an attendee. - * - * This function figures out if we need to send a reply to an organizer. - * - * @param VCalendar $calendar - * @param array $eventInfo - * @param array $oldEventInfo - * @param string $attendee - * @return Message[] - */ - protected function parseEventForAttendee(VCalendar $calendar, array $eventInfo, array $oldEventInfo, $attendee) { - - if ($this->scheduleAgentServerRules && $eventInfo['organizerScheduleAgent']==='CLIENT') { - return array(); - } - - // Don't bother generating messages for events that have already been - // cancelled. - if ($eventInfo['status']==='CANCELLED') { - return array(); - } - - $instances = array(); - foreach($oldEventInfo['attendees'][$attendee]['instances'] as $instance) { - - $instances[$instance['id']] = array( - 'id' => $instance['id'], - 'oldstatus' => $instance['partstat'], - 'newstatus' => null, - ); - - } - foreach($eventInfo['attendees'][$attendee]['instances'] as $instance) { - - if (isset($instances[$instance['id']])) { - $instances[$instance['id']]['newstatus'] = $instance['partstat']; - } else { - $instances[$instance['id']] = array( - 'id' => $instance['id'], - 'oldstatus' => null, - 'newstatus' => $instance['partstat'], - ); - } - - } - - // We need to also look for differences in EXDATE. If there are new - // items in EXDATE, it means that an attendee deleted instances of an - // event, which means we need to send DECLINED specifically for those - // instances. - // We only need to do that though, if the master event is not declined. - if ($instances['master']['newstatus'] !== 'DECLINED') { - foreach($eventInfo['exdate'] as $exDate) { - - if (!in_array($exDate, $oldEventInfo['exdate'])) { - if (isset($instances[$exDate])) { - $instances[$exDate]['newstatus'] = 'DECLINED'; - } else { - $instances[$exDate] = array( - 'id' => $exDate, - 'oldstatus' => null, - 'newstatus' => 'DECLINED', - ); - } - } - - } - } - - // Gathering a few extra properties for each instance. - foreach($instances as $recurId=>$instanceInfo) { - - if (isset($eventInfo['instances'][$recurId])) { - $instances[$recurId]['dtstart'] = clone $eventInfo['instances'][$recurId]->DTSTART; - } else { - $instances[$recurId]['dtstart'] = $recurId; - } - - } - - $message = new Message(); - $message->uid = $eventInfo['uid']; - $message->method = 'REPLY'; - $message->component = 'VEVENT'; - $message->sequence = $eventInfo['sequence']; - $message->sender = $attendee; - $message->senderName = $eventInfo['attendees'][$attendee]['name']; - $message->recipient = $eventInfo['organizer']; - $message->recipientName = $eventInfo['organizerName']; - - $icalMsg = new VCalendar(); - $icalMsg->METHOD = 'REPLY'; - - $hasReply = false; - - foreach($instances as $instance) { - - if ($instance['oldstatus']==$instance['newstatus'] && $eventInfo['organizerForceSend'] !== 'REPLY') { - // Skip - continue; - } - - $event = $icalMsg->add('VEVENT', array( - 'UID' => $message->uid, - 'SEQUENCE' => $message->sequence, - )); - $summary = isset($calendar->VEVENT->SUMMARY)?$calendar->VEVENT->SUMMARY->getValue():''; - // Adding properties from the correct source instance - if (isset($eventInfo['instances'][$instance['id']])) { - $instanceObj = $eventInfo['instances'][$instance['id']]; - $event->add(clone $instanceObj->DTSTART); - if (isset($instanceObj->SUMMARY)) { - $event->add('SUMMARY', $instanceObj->SUMMARY->getValue()); - } elseif ($summary) { - $event->add('SUMMARY', $summary); - } - } else { - // This branch of the code is reached, when a reply is - // generated for an instance of a recurring event, through the - // fact that the instance has disappeared by showing up in - // EXDATE - $dt = DateTimeParser::parse($instance['id'], $eventInfo['timezone']); - // Treat is as a DATE field - if (strlen($instance['id']) <= 8) { - $recur = $event->add('DTSTART', $dt, array('VALUE' => 'DATE')); - } else { - $recur = $event->add('DTSTART', $dt); - } - if ($summary) { - $event->add('SUMMARY', $summary); - } - } - if ($instance['id'] !== 'master') { - $dt = DateTimeParser::parse($instance['id'], $eventInfo['timezone']); - // Treat is as a DATE field - if (strlen($instance['id']) <= 8) { - $recur = $event->add('RECURRENCE-ID', $dt, array('VALUE' => 'DATE')); - } else { - $recur = $event->add('RECURRENCE-ID', $dt); - } - } - $organizer = $event->add('ORGANIZER', $message->recipient); - if ($message->recipientName) { - $organizer['CN'] = $message->recipientName; - } - $attendee = $event->add('ATTENDEE', $message->sender, array( - 'PARTSTAT' => $instance['newstatus'] - )); - if ($message->senderName) { - $attendee['CN'] = $message->senderName; - } - $hasReply = true; - - } - - if ($hasReply) { - $message->message = $icalMsg; - return array($message); - } else { - return array(); - } - - } - - /** - * Returns attendee information and information about instances of an - * event. - * - * Returns an array with the following keys: - * - * 1. uid - * 2. organizer - * 3. organizerName - * 4. attendees - * 5. instances - * - * @param VCalendar $calendar - * @return array - */ - protected function parseEventInfo(VCalendar $calendar = null) { - - $uid = null; - $organizer = null; - $organizerName = null; - $organizerForceSend = null; - $sequence = null; - $timezone = null; - $status = null; - $organizerScheduleAgent = 'SERVER'; - - $significantChangeHash = ''; - - // Now we need to collect a list of attendees, and which instances they - // are a part of. - $attendees = array(); - - $instances = array(); - $exdate = array(); - - foreach($calendar->VEVENT as $vevent) { - - if (is_null($uid)) { - $uid = $vevent->UID->getValue(); - } else { - if ($uid !== $vevent->UID->getValue()) { - throw new ITipException('If a calendar contained more than one event, they must have the same UID.'); - } - } - - if (!isset($vevent->DTSTART)) { - throw new ITipException('An event MUST have a DTSTART property.'); - } - - if (isset($vevent->ORGANIZER)) { - if (is_null($organizer)) { - $organizer = $vevent->ORGANIZER->getNormalizedValue(); - $organizerName = isset($vevent->ORGANIZER['CN'])?$vevent->ORGANIZER['CN']:null; - } else { - if ($organizer !== $vevent->ORGANIZER->getNormalizedValue()) { - throw new SameOrganizerForAllComponentsException('Every instance of the event must have the same organizer.'); - } - } - $organizerForceSend = - isset($vevent->ORGANIZER['SCHEDULE-FORCE-SEND']) ? - strtoupper($vevent->ORGANIZER['SCHEDULE-FORCE-SEND']) : - null; - $organizerScheduleAgent = - isset($vevent->ORGANIZER['SCHEDULE-AGENT']) ? - strtoupper((string)$vevent->ORGANIZER['SCHEDULE-AGENT']) : - 'SERVER'; - } - if (is_null($sequence) && isset($vevent->SEQUENCE)) { - $sequence = $vevent->SEQUENCE->getValue(); - } - if (isset($vevent->EXDATE)) { - $exdate = $vevent->EXDATE->getParts(); - } - if (isset($vevent->STATUS)) { - $status = strtoupper($vevent->STATUS->getValue()); - } - - $recurId = isset($vevent->{'RECURRENCE-ID'})?$vevent->{'RECURRENCE-ID'}->getValue():'master'; - if ($recurId==='master') { - $timezone = $vevent->DTSTART->getDateTime()->getTimeZone(); - } - if(isset($vevent->ATTENDEE)) { - foreach($vevent->ATTENDEE as $attendee) { - - if ($this->scheduleAgentServerRules && - isset($attendee['SCHEDULE-AGENT']) && - strtoupper($attendee['SCHEDULE-AGENT']->getValue()) === 'CLIENT' - ) { - continue; - } - $partStat = - isset($attendee['PARTSTAT']) ? - strtoupper($attendee['PARTSTAT']) : - 'NEEDS-ACTION'; - - $forceSend = - isset($attendee['SCHEDULE-FORCE-SEND']) ? - strtoupper($attendee['SCHEDULE-FORCE-SEND']) : - null; - - - if (isset($attendees[$attendee->getNormalizedValue()])) { - $attendees[$attendee->getNormalizedValue()]['instances'][$recurId] = array( - 'id' => $recurId, - 'partstat' => $partStat, - 'force-send' => $forceSend, - ); - } else { - $attendees[$attendee->getNormalizedValue()] = array( - 'href' => $attendee->getNormalizedValue(), - 'instances' => array( - $recurId => array( - 'id' => $recurId, - 'partstat' => $partStat, - ), - ), - 'name' => isset($attendee['CN'])?(string)$attendee['CN']:null, - 'forceSend' => $forceSend, - ); - } - - } - $instances[$recurId] = $vevent; - - } - - foreach($this->significantChangeProperties as $prop) { - if (isset($vevent->$prop)) { - $significantChangeHash.=$prop.':'; - foreach($vevent->select($prop) as $val) { - $significantChangeHash.= $val->getValue().';'; - } - } - } - - } - $significantChangeHash = md5($significantChangeHash); - - return compact( - 'uid', - 'organizer', - 'organizerName', - 'organizerScheduleAgent', - 'organizerForceSend', - 'instances', - 'attendees', - 'sequence', - 'exdate', - 'timezone', - 'significantChangeHash', - 'status' - ); - - } - -}
--- a/vendor/sabre/vobject/lib/ITip/ITipException.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,15 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -use Exception; - -/** - * This message is emitted in case of serious problems with iTip messages. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class ITipException extends Exception { -}
--- a/vendor/sabre/vobject/lib/ITip/Message.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,141 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -/** - * This class represents an iTip message - * - * A message holds all the information relevant to the message, including the - * object itself. - * - * It should for the most part be treated as immutable. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Message { - - /** - * The object's UID - * - * @var string - */ - public $uid; - - /** - * The component type, such as VEVENT - * - * @var string - */ - public $component; - - /** - * Contains the ITip method, which is something like REQUEST, REPLY or - * CANCEL. - * - * @var string - */ - public $method; - - /** - * The current sequence number for the event. - * - * @var int - */ - public $sequence; - - /** - * The senders' email address. - * - * Note that this does not imply that this has to be used in a From: field - * if the message is sent by email. It may also be populated in Reply-To: - * or not at all. - * - * @var string - */ - public $sender; - - /** - * The name of the sender. This is often populated from a CN parameter from - * either the ORGANIZER or ATTENDEE, depending on the message. - * - * @var string|null - */ - public $senderName; - - /** - * The recipient's email address. - * - * @var string - */ - public $recipient; - - /** - * The name of the recipient. This is usually populated with the CN - * parameter from the ATTENDEE or ORGANIZER property, if it's available. - * - * @var string|null - */ - public $recipientName; - - /** - * After the message has been delivered, this should contain a string such - * as : 1.1;Sent or 1.2;Delivered. - * - * In case of a failure, this will hold the error status code. - * - * See: - * http://tools.ietf.org/html/rfc6638#section-7.3 - * - * @var string - */ - public $scheduleStatus; - - /** - * The iCalendar / iTip body. - * - * @var \Sabre\VObject\Component\VCalendar - */ - public $message; - - /** - * This will be set to true, if the iTip broker considers the change - * 'significant'. - * - * In practice, this means that we'll only mark it true, if for instance - * DTSTART changed. This allows systems to only send iTip messages when - * significant changes happened. This is especially useful for iMip, as - * normally a ton of messages may be generated for normal calendar use. - * - * To see the list of properties that are considered 'significant', check - * out Sabre\VObject\ITip\Broker::$significantChangeProperties. - * - * @var bool - */ - public $significantChange = true; - - /** - * Returns the schedule status as a string. - * - * For example: - * 1.2 - * - * @return mixed bool|string - */ - public function getScheduleStatus() { - - if(!$this->scheduleStatus) { - - return false; - - } else { - - list($scheduleStatus) = explode(';', $this->scheduleStatus); - return $scheduleStatus; - - } - - } - -}
--- a/vendor/sabre/vobject/lib/ITip/SameOrganizerForAllComponentsException.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,18 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -/** - * SameOrganizerForAllComponentsException - * - * This exception is emitted when an event is encountered with more than one - * component (e.g.: exceptions), but the organizer is not identical in every - * component. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class SameOrganizerForAllComponentsException extends ITipException { - -}
--- a/vendor/sabre/vobject/lib/Node.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,226 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * A node is the root class for every element in an iCalendar of vCard object. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -abstract class Node implements \IteratorAggregate, \ArrayAccess, \Countable { - - /** - * The following constants are used by the validate() method. - * - * If REPAIR is set, the validator will attempt to repair any broken data - * (if possible). - */ - const REPAIR = 1; - - /** - * If this option is set, the validator will operate on the vcards on the - * assumption that the vcards need to be valid for CardDAV. - * - * This means for example that the UID is required, whereas it is not for - * regular vcards. - */ - const PROFILE_CARDDAV = 2; - - /** - * If this option is set, the validator will operate on iCalendar objects - * on the assumption that the vcards need to be valid for CalDAV. - * - * This means for example that calendars can only contain objects with - * identical component types and UIDs. - */ - const PROFILE_CALDAV = 4; - - /** - * Reference to the parent object, if this is not the top object. - * - * @var Node - */ - public $parent; - - /** - * Iterator override - * - * @var ElementList - */ - protected $iterator = null; - - /** - * The root document - * - * @var Component - */ - protected $root; - - /** - * Serializes the node into a mimedir format - * - * @return string - */ - abstract public function serialize(); - - /** - * This method returns an array, with the representation as it should be - * encoded in json. This is used to create jCard or jCal documents. - * - * @return array - */ - abstract public function jsonSerialize(); - - /* {{{ IteratorAggregator interface */ - - /** - * Returns the iterator for this object - * - * @return ElementList - */ - public function getIterator() { - - if (!is_null($this->iterator)) - return $this->iterator; - - return new ElementList(array($this)); - - } - - /** - * Sets the overridden iterator - * - * Note that this is not actually part of the iterator interface - * - * @param ElementList $iterator - * @return void - */ - public function setIterator(ElementList $iterator) { - - $this->iterator = $iterator; - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * Node::REPAIR - May attempt to automatically repair the problem. - * - * This method returns an array with detected problems. - * Every element has the following properties: - * - * * level - problem level. - * * message - A human-readable string describing the issue. - * * node - A reference to the problematic node. - * - * The level means: - * 1 - The issue was repaired (only happens if REPAIR was turned on) - * 2 - An inconsequential issue - * 3 - A severe issue. - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - return array(); - - } - - /* }}} */ - - /* {{{ Countable interface */ - - /** - * Returns the number of elements - * - * @return int - */ - public function count() { - - $it = $this->getIterator(); - return $it->count(); - - } - - /* }}} */ - - /* {{{ ArrayAccess Interface */ - - - /** - * Checks if an item exists through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @return bool - */ - public function offsetExists($offset) { - - $iterator = $this->getIterator(); - return $iterator->offsetExists($offset); - - } - - /** - * Gets an item through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @return mixed - */ - public function offsetGet($offset) { - - $iterator = $this->getIterator(); - return $iterator->offsetGet($offset); - - } - - /** - * Sets an item through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @param mixed $value - * @return void - */ - public function offsetSet($offset, $value) { - - $iterator = $this->getIterator(); - $iterator->offsetSet($offset,$value); - - // @codeCoverageIgnoreStart - // - // This method always throws an exception, so we ignore the closing - // brace - } - // @codeCoverageIgnoreEnd - - /** - * Sets an item through ArrayAccess. - * - * This method just forwards the request to the inner iterator - * - * @param int $offset - * @return void - */ - public function offsetUnset($offset) { - - $iterator = $this->getIterator(); - $iterator->offsetUnset($offset); - - // @codeCoverageIgnoreStart - // - // This method always throws an exception, so we ignore the closing - // brace - } - // @codeCoverageIgnoreEnd - - /* }}} */ -}
--- a/vendor/sabre/vobject/lib/Parameter.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,373 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - ArrayObject; - -/** - * VObject Parameter - * - * This class represents a parameter. A parameter is always tied to a property. - * In the case of: - * DTSTART;VALUE=DATE:20101108 - * VALUE=DATE would be the parameter name and value. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Parameter extends Node { - - /** - * Parameter name - * - * @var string - */ - public $name; - - /** - * vCard 2.1 allows parameters to be encoded without a name. - * - * We can deduce the parameter name based on it's value. - * - * @var bool - */ - public $noName = false; - - /** - * Parameter value - * - * @var string - */ - protected $value; - - /** - * Sets up the object. - * - * It's recommended to use the create:: factory method instead. - * - * @param string $name - * @param string $value - */ - public function __construct(Document $root, $name, $value = null) { - - $this->name = strtoupper($name); - $this->root = $root; - if (is_null($name)) { - $this->noName = true; - $this->name = static::guessParameterNameByValue($value); - } - - // If guessParameterNameByValue() returns an empty string - // above, we're actually dealing with a parameter that has no value. - // In that case we have to move the value to the name. - if ($this->name === '') { - $this->noName = false; - $this->name = strtoupper($value); - } else { - $this->setValue($value); - } - - } - - /** - * Try to guess property name by value, can be used for vCard 2.1 nameless parameters. - * - * Figuring out what the name should have been. Note that a ton of - * these are rather silly in 2014 and would probably rarely be - * used, but we like to be complete. - * - * @param string $value - * @return string - */ - public static function guessParameterNameByValue($value) { - switch(strtoupper($value)) { - - // Encodings - case '7-BIT' : - case 'QUOTED-PRINTABLE' : - case 'BASE64' : - $name = 'ENCODING'; - break; - - // Common types - case 'WORK' : - case 'HOME' : - case 'PREF' : - - // Delivery Label Type - case 'DOM' : - case 'INTL' : - case 'POSTAL' : - case 'PARCEL' : - - // Telephone types - case 'VOICE' : - case 'FAX' : - case 'MSG' : - case 'CELL' : - case 'PAGER' : - case 'BBS' : - case 'MODEM' : - case 'CAR' : - case 'ISDN' : - case 'VIDEO' : - - // EMAIL types (lol) - case 'AOL' : - case 'APPLELINK' : - case 'ATTMAIL' : - case 'CIS' : - case 'EWORLD' : - case 'INTERNET' : - case 'IBMMAIL' : - case 'MCIMAIL' : - case 'POWERSHARE' : - case 'PRODIGY' : - case 'TLX' : - case 'X400' : - - // Photo / Logo format types - case 'GIF' : - case 'CGM' : - case 'WMF' : - case 'BMP' : - case 'DIB' : - case 'PICT' : - case 'TIFF' : - case 'PDF ': - case 'PS' : - case 'JPEG' : - case 'MPEG' : - case 'MPEG2' : - case 'AVI' : - case 'QTIME' : - - // Sound Digital Audio Type - case 'WAVE' : - case 'PCM' : - case 'AIFF' : - - // Key types - case 'X509' : - case 'PGP' : - $name = 'TYPE'; - break; - - // Value types - case 'INLINE' : - case 'URL' : - case 'CONTENT-ID' : - case 'CID' : - $name = 'VALUE'; - break; - - default: - $name = ''; - } - - return $name; - } - - /** - * Updates the current value. - * - * This may be either a single, or multiple strings in an array. - * - * @param string|array $value - * @return void - */ - public function setValue($value) { - - $this->value = $value; - - } - - /** - * Returns the current value - * - * This method will always return a string, or null. If there were multiple - * values, it will automatically concatinate them (separated by comma). - * - * @return string|null - */ - public function getValue() { - - if (is_array($this->value)) { - return implode(',' , $this->value); - } else { - return $this->value; - } - - } - - /** - * Sets multiple values for this parameter. - * - * @param array $value - * @return void - */ - public function setParts(array $value) { - - $this->value = $value; - - } - - /** - * Returns all values for this parameter. - * - * If there were no values, an empty array will be returned. - * - * @return array - */ - public function getParts() { - - if (is_array($this->value)) { - return $this->value; - } elseif (is_null($this->value)) { - return array(); - } else { - return array($this->value); - } - - } - - /** - * Adds a value to this parameter - * - * If the argument is specified as an array, all items will be added to the - * parameter value list. - * - * @param string|array $part - * @return void - */ - public function addValue($part) { - - if (is_null($this->value)) { - $this->value = $part; - } else { - $this->value = array_merge((array)$this->value, (array)$part); - } - - } - - /** - * Checks if this parameter contains the specified value. - * - * This is a case-insensitive match. It makes sense to call this for for - * instance the TYPE parameter, to see if it contains a keyword such as - * 'WORK' or 'FAX'. - * - * @param string $value - * @return bool - */ - public function has($value) { - - return in_array( - strtolower($value), - array_map('strtolower', (array)$this->value) - ); - - } - - /** - * Turns the object back into a serialized blob. - * - * @return string - */ - public function serialize() { - - $value = $this->getParts(); - - if (count($value)===0) { - return $this->name . '='; - } - - if ($this->root->getDocumentType() === Document::VCARD21 && $this->noName) { - - return implode(';', $value); - - } - - return $this->name . '=' . array_reduce( - $value, - function($out, $item) { - - if (!is_null($out)) $out.=','; - - // If there's no special characters in the string, we'll use the simple - // format. - // - // The list of special characters is defined as: - // - // Any character except CONTROL, DQUOTE, ";", ":", "," - // - // by the iCalendar spec: - // https://tools.ietf.org/html/rfc5545#section-3.1 - // - // And we add ^ to that because of: - // https://tools.ietf.org/html/rfc6868 - // - // But we've found that iCal (7.0, shipped with OSX 10.9) - // severaly trips on + characters not being quoted, so we - // added + as well. - if (!preg_match('#(?: [\n":;\^,\+] )#x', $item)) { - return $out.$item; - } else { - // Enclosing in double-quotes, and using RFC6868 for encoding any - // special characters - $out.='"' . strtr( - $item, - array( - '^' => '^^', - "\n" => '^n', - '"' => '^\'', - ) - ) . '"'; - return $out; - } - - } - ); - - } - - /** - * This method returns an array, with the representation as it should be - * encoded in json. This is used to create jCard or jCal documents. - * - * @return array - */ - public function jsonSerialize() { - - return $this->value; - - } - - /** - * Called when this object is being cast to a string - * - * @return string - */ - public function __toString() { - - return (string)$this->getValue(); - - } - - /** - * Returns the iterator for this object - * - * @return ElementList - */ - public function getIterator() { - - if (!is_null($this->iterator)) - return $this->iterator; - - return $this->iterator = new ArrayObject((array)$this->value); - - } - -}
--- a/vendor/sabre/vobject/lib/ParseException.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,13 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Exception thrown by Reader if an invalid object was attempted to be parsed. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class ParseException extends \Exception { -}
--- a/vendor/sabre/vobject/lib/Parser/Json.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,194 +0,0 @@ -<?php - -namespace Sabre\VObject\Parser; - -use - Sabre\VObject\Component\VCalendar, - Sabre\VObject\Component\VCard, - Sabre\VObject\ParseException, - Sabre\VObject\EofException; - -/** - * Json Parser. - * - * This parser parses both the jCal and jCard formats. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Json extends Parser { - - /** - * The input data - * - * @var array - */ - protected $input; - - /** - * Root component - * - * @var Document - */ - protected $root; - - /** - * This method starts the parsing process. - * - * If the input was not supplied during construction, it's possible to pass - * it here instead. - * - * If either input or options are not supplied, the defaults will be used. - * - * @param resource|string|array|null $input - * @param int|null $options - * @return array - */ - public function parse($input = null, $options = null) { - - if (!is_null($input)) { - $this->setInput($input); - } - if (is_null($this->input)) { - throw new EofException('End of input stream, or no input supplied'); - } - - if (!is_null($options)) { - $this->options = $options; - } - - switch($this->input[0]) { - case 'vcalendar' : - $this->root = new VCalendar(array(), false); - break; - case 'vcard' : - $this->root = new VCard(array(), false); - break; - default : - throw new ParseException('The root component must either be a vcalendar, or a vcard'); - - } - foreach($this->input[1] as $prop) { - $this->root->add($this->parseProperty($prop)); - } - if (isset($this->input[2])) foreach($this->input[2] as $comp) { - $this->root->add($this->parseComponent($comp)); - } - - // Resetting the input so we can throw an feof exception the next time. - $this->input = null; - - return $this->root; - - } - - /** - * Parses a component - * - * @param array $jComp - * @return \Sabre\VObject\Component - */ - public function parseComponent(array $jComp) { - - // We can remove $self from PHP 5.4 onward. - $self = $this; - - $properties = array_map( - function($jProp) use ($self) { - return $self->parseProperty($jProp); - }, - $jComp[1] - ); - - if (isset($jComp[2])) { - - $components = array_map( - function($jComp) use ($self) { - return $self->parseComponent($jComp); - }, - $jComp[2] - ); - - } else $components = array(); - - return $this->root->createComponent( - $jComp[0], - array_merge($properties, $components), - $defaults = false - ); - - } - - /** - * Parses properties. - * - * @param array $jProp - * @return \Sabre\VObject\Property - */ - public function parseProperty(array $jProp) { - - list( - $propertyName, - $parameters, - $valueType - ) = $jProp; - - $propertyName = strtoupper($propertyName); - - // This is the default class we would be using if we didn't know the - // value type. We're using this value later in this function. - $defaultPropertyClass = $this->root->getClassNameForPropertyName($propertyName); - - $parameters = (array)$parameters; - - $value = array_slice($jProp, 3); - - $valueType = strtoupper($valueType); - - if (isset($parameters['group'])) { - $propertyName = $parameters['group'] . '.' . $propertyName; - unset($parameters['group']); - } - - $prop = $this->root->createProperty($propertyName, null, $parameters, $valueType); - $prop->setJsonValue($value); - - // We have to do something awkward here. FlatText as well as Text - // represents TEXT values. We have to normalize these here. In the - // future we can get rid of FlatText once we're allowed to break BC - // again. - if ($defaultPropertyClass === 'Sabre\VObject\Property\FlatText') { - $defaultPropertyClass = 'Sabre\VObject\Property\Text'; - } - - // If the value type we received (e.g.: TEXT) was not the default value - // type for the given property (e.g.: BDAY), we need to add a VALUE= - // parameter. - if ($defaultPropertyClass !== get_class($prop)) { - $prop["VALUE"] = $valueType; - } - - return $prop; - - } - - /** - * Sets the input data - * - * @param resource|string|array $input - * @return void - */ - public function setInput($input) { - - if (is_resource($input)) { - $input = stream_get_contents($input); - } - if (is_string($input)) { - $input = json_decode($input); - } - $this->input = $input; - - } - -}
--- a/vendor/sabre/vobject/lib/Parser/MimeDir.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,628 +0,0 @@ -<?php - -namespace Sabre\VObject\Parser; - -use - Sabre\VObject\ParseException, - Sabre\VObject\EofException, - Sabre\VObject\Component, - Sabre\VObject\Property, - Sabre\VObject\Component\VCalendar, - Sabre\VObject\Component\VCard; - -/** - * MimeDir parser. - * - * This class parses iCalendar 2.0 and vCard 2.1, 3.0 and 4.0 files. This - * parser will return one of the following two objects from the parse method: - * - * Sabre\VObject\Component\VCalendar - * Sabre\VObject\Component\VCard - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class MimeDir extends Parser { - - /** - * The input stream. - * - * @var resource - */ - protected $input; - - /** - * Root component - * - * @var Component - */ - protected $root; - - /** - * Parses an iCalendar or vCard file - * - * Pass a stream or a string. If null is parsed, the existing buffer is - * used. - * - * @param string|resource|null $input - * @param int|null $options - * @return array - */ - public function parse($input = null, $options = null) { - - $this->root = null; - if (!is_null($input)) { - - $this->setInput($input); - - } - - if (!is_null($options)) $this->options = $options; - - $this->parseDocument(); - - return $this->root; - - } - - /** - * Sets the input buffer. Must be a string or stream. - * - * @param resource|string $input - * @return void - */ - public function setInput($input) { - - // Resetting the parser - $this->lineIndex = 0; - $this->startLine = 0; - - if (is_string($input)) { - // Convering to a stream. - $stream = fopen('php://temp', 'r+'); - fwrite($stream, $input); - rewind($stream); - $this->input = $stream; - } elseif (is_resource($input)) { - $this->input = $input; - } else { - throw new \InvalidArgumentException('This parser can only read from strings or streams.'); - } - - } - - /** - * Parses an entire document. - * - * @return void - */ - protected function parseDocument() { - - $line = $this->readLine(); - - // BOM is ZERO WIDTH NO-BREAK SPACE (U+FEFF). - // It's 0xEF 0xBB 0xBF in UTF-8 hex. - if ( 3 <= strlen($line) - && ord($line[0]) === 0xef - && ord($line[1]) === 0xbb - && ord($line[2]) === 0xbf) { - $line = substr($line, 3); - } - - switch(strtoupper($line)) { - case 'BEGIN:VCALENDAR' : - $class = isset(VCalendar::$componentMap['VCALENDAR']) - ? VCalendar::$componentMap[$name] - : 'Sabre\\VObject\\Component\\VCalendar'; - break; - case 'BEGIN:VCARD' : - $class = isset(VCard::$componentMap['VCARD']) - ? VCard::$componentMap['VCARD'] - : 'Sabre\\VObject\\Component\\VCard'; - break; - default : - throw new ParseException('This parser only supports VCARD and VCALENDAR files'); - } - - $this->root = new $class(array(), false); - - while(true) { - - // Reading until we hit END: - $line = $this->readLine(); - if (strtoupper(substr($line,0,4)) === 'END:') { - break; - } - $result = $this->parseLine($line); - if ($result) { - $this->root->add($result); - } - - } - - $name = strtoupper(substr($line, 4)); - if ($name!==$this->root->name) { - throw new ParseException('Invalid MimeDir file. expected: "END:' . $this->root->name . '" got: "END:' . $name . '"'); - } - - } - - /** - * Parses a line, and if it hits a component, it will also attempt to parse - * the entire component - * - * @param string $line Unfolded line - * @return Node - */ - protected function parseLine($line) { - - // Start of a new component - if (strtoupper(substr($line, 0, 6)) === 'BEGIN:') { - - $component = $this->root->createComponent(substr($line,6), array(), false); - - while(true) { - - // Reading until we hit END: - $line = $this->readLine(); - if (strtoupper(substr($line,0,4)) === 'END:') { - break; - } - $result = $this->parseLine($line); - if ($result) { - $component->add($result); - } - - } - - $name = strtoupper(substr($line, 4)); - if ($name!==$component->name) { - throw new ParseException('Invalid MimeDir file. expected: "END:' . $component->name . '" got: "END:' . $name . '"'); - } - - return $component; - - } else { - - // Property reader - $property = $this->readProperty($line); - if (!$property) { - // Ignored line - return false; - } - return $property; - - } - - } - - /** - * We need to look ahead 1 line every time to see if we need to 'unfold' - * the next line. - * - * If that was not the case, we store it here. - * - * @var null|string - */ - protected $lineBuffer; - - /** - * The real current line number. - */ - protected $lineIndex = 0; - - /** - * In the case of unfolded lines, this property holds the line number for - * the start of the line. - * - * @var int - */ - protected $startLine = 0; - - /** - * Contains a 'raw' representation of the current line. - * - * @var string - */ - protected $rawLine; - - /** - * Reads a single line from the buffer. - * - * This method strips any newlines and also takes care of unfolding. - * - * @throws \Sabre\VObject\EofException - * @return string - */ - protected function readLine() { - - if (!is_null($this->lineBuffer)) { - $rawLine = $this->lineBuffer; - $this->lineBuffer = null; - } else { - do { - $eof = feof($this->input); - - $rawLine = fgets($this->input); - - if ($eof || (feof($this->input) && $rawLine===false)) { - throw new EofException('End of document reached prematurely'); - } - if ($rawLine === false) { - throw new ParseException('Error reading from input stream'); - } - $rawLine = rtrim($rawLine, "\r\n"); - } while ($rawLine === ''); // Skipping empty lines - $this->lineIndex++; - } - $line = $rawLine; - - $this->startLine = $this->lineIndex; - - // Looking ahead for folded lines. - while (true) { - - $nextLine = rtrim(fgets($this->input), "\r\n"); - $this->lineIndex++; - if (!$nextLine) { - break; - } - if ($nextLine[0] === "\t" || $nextLine[0] === " ") { - $line .= substr($nextLine, 1); - $rawLine .= "\n " . substr($nextLine, 1); - } else { - $this->lineBuffer = $nextLine; - break; - } - - } - $this->rawLine = $rawLine; - return $line; - - } - - /** - * Reads a property or component from a line. - * - * @return void - */ - protected function readProperty($line) { - - if ($this->options & self::OPTION_FORGIVING) { - $propNameToken = 'A-Z0-9\-\._\\/'; - } else { - $propNameToken = 'A-Z0-9\-\.'; - } - - $paramNameToken = 'A-Z0-9\-'; - $safeChar = '^";:,'; - $qSafeChar = '^"'; - - $regex = "/ - ^(?P<name> [$propNameToken]+ ) (?=[;:]) # property name - | - (?<=:)(?P<propValue> .+)$ # property value - | - ;(?P<paramName> [$paramNameToken]+) (?=[=;:]) # parameter name - | - (=|,)(?P<paramValue> # parameter value - (?: [$safeChar]*) | - \"(?: [$qSafeChar]+)\" - ) (?=[;:,]) - /xi"; - - //echo $regex, "\n"; die(); - preg_match_all($regex, $line, $matches, PREG_SET_ORDER); - - $property = array( - 'name' => null, - 'parameters' => array(), - 'value' => null - ); - - $lastParam = null; - - /** - * Looping through all the tokens. - * - * Note that we are looping through them in reverse order, because if a - * sub-pattern matched, the subsequent named patterns will not show up - * in the result. - */ - foreach($matches as $match) { - - if (isset($match['paramValue'])) { - if ($match['paramValue'] && $match['paramValue'][0] === '"') { - $value = substr($match['paramValue'], 1, -1); - } else { - $value = $match['paramValue']; - } - - $value = $this->unescapeParam($value); - - if (is_null($property['parameters'][$lastParam])) { - $property['parameters'][$lastParam] = $value; - } elseif (is_array($property['parameters'][$lastParam])) { - $property['parameters'][$lastParam][] = $value; - } else { - $property['parameters'][$lastParam] = array( - $property['parameters'][$lastParam], - $value - ); - } - continue; - } - if (isset($match['paramName'])) { - $lastParam = strtoupper($match['paramName']); - if (!isset($property['parameters'][$lastParam])) { - $property['parameters'][$lastParam] = null; - } - continue; - } - if (isset($match['propValue'])) { - $property['value'] = $match['propValue']; - continue; - } - if (isset($match['name']) && $match['name']) { - $property['name'] = strtoupper($match['name']); - continue; - } - - // @codeCoverageIgnoreStart - throw new \LogicException('This code should not be reachable'); - // @codeCoverageIgnoreEnd - - } - - if (is_null($property['value'])) { - $property['value'] = ''; - } - if (!$property['name']) { - if ($this->options & self::OPTION_IGNORE_INVALID_LINES) { - return false; - } - throw new ParseException('Invalid Mimedir file. Line starting at ' . $this->startLine . ' did not follow iCalendar/vCard conventions'); - } - - // vCard 2.1 states that parameters may appear without a name, and only - // a value. We can deduce the value based on it's name. - // - // Our parser will get those as parameters without a value instead, so - // we're filtering these parameters out first. - $namedParameters = array(); - $namelessParameters = array(); - - foreach($property['parameters'] as $name=>$value) { - if (!is_null($value)) { - $namedParameters[$name] = $value; - } else { - $namelessParameters[] = $name; - } - } - - $propObj = $this->root->createProperty($property['name'], null, $namedParameters); - - foreach($namelessParameters as $namelessParameter) { - $propObj->add(null, $namelessParameter); - } - - if (strtoupper($propObj['ENCODING']) === 'QUOTED-PRINTABLE') { - $propObj->setQuotedPrintableValue($this->extractQuotedPrintableValue()); - } else { - $propObj->setRawMimeDirValue($property['value']); - } - - return $propObj; - - } - - /** - * Unescapes a property value. - * - * vCard 2.1 says: - * * Semi-colons must be escaped in some property values, specifically - * ADR, ORG and N. - * * Semi-colons must be escaped in parameter values, because semi-colons - * are also use to separate values. - * * No mention of escaping backslashes with another backslash. - * * newlines are not escaped either, instead QUOTED-PRINTABLE is used to - * span values over more than 1 line. - * - * vCard 3.0 says: - * * (rfc2425) Backslashes, newlines (\n or \N) and comma's must be - * escaped, all time time. - * * Comma's are used for delimeters in multiple values - * * (rfc2426) Adds to to this that the semi-colon MUST also be escaped, - * as in some properties semi-colon is used for separators. - * * Properties using semi-colons: N, ADR, GEO, ORG - * * Both ADR and N's individual parts may be broken up further with a - * comma. - * * Properties using commas: NICKNAME, CATEGORIES - * - * vCard 4.0 (rfc6350) says: - * * Commas must be escaped. - * * Semi-colons may be escaped, an unescaped semi-colon _may_ be a - * delimiter, depending on the property. - * * Backslashes must be escaped - * * Newlines must be escaped as either \N or \n. - * * Some compound properties may contain multiple parts themselves, so a - * comma within a semi-colon delimited property may also be unescaped - * to denote multiple parts _within_ the compound property. - * * Text-properties using semi-colons: N, ADR, ORG, CLIENTPIDMAP. - * * Text-properties using commas: NICKNAME, RELATED, CATEGORIES, PID. - * - * Even though the spec says that commas must always be escaped, the - * example for GEO in Section 6.5.2 seems to violate this. - * - * iCalendar 2.0 (rfc5545) says: - * * Commas or semi-colons may be used as delimiters, depending on the - * property. - * * Commas, semi-colons, backslashes, newline (\N or \n) are always - * escaped, unless they are delimiters. - * * Colons shall not be escaped. - * * Commas can be considered the 'default delimiter' and is described as - * the delimiter in cases where the order of the multiple values is - * insignificant. - * * Semi-colons are described as the delimiter for 'structured values'. - * They are specifically used in Semi-colons are used as a delimiter in - * REQUEST-STATUS, RRULE, GEO and EXRULE. EXRULE is deprecated however. - * - * Now for the parameters - * - * If delimiter is not set (null) this method will just return a string. - * If it's a comma or a semi-colon the string will be split on those - * characters, and always return an array. - * - * @param string $input - * @param string $delimiter - * @return string|string[] - */ - static public function unescapeValue($input, $delimiter = ';') { - - $regex = '# (?: (\\\\ (?: \\\\ | N | n | ; | , ) )'; - if ($delimiter) { - $regex .= ' | (' . $delimiter . ')'; - } - $regex .= ') #x'; - - $matches = preg_split($regex, $input, -1, PREG_SPLIT_DELIM_CAPTURE | PREG_SPLIT_NO_EMPTY); - - $resultArray = array(); - $result = ''; - - foreach($matches as $match) { - - switch ($match) { - case '\\\\' : - $result .='\\'; - break; - case '\N' : - case '\n' : - $result .="\n"; - break; - case '\;' : - $result .=';'; - break; - case '\,' : - $result .=','; - break; - case $delimiter : - $resultArray[] = $result; - $result = ''; - break; - default : - $result .= $match; - break; - - } - - } - - $resultArray[] = $result; - return $delimiter ? $resultArray : $result; - - } - - /** - * Unescapes a parameter value. - * - * vCard 2.1: - * * Does not mention a mechanism for this. In addition, double quotes - * are never used to wrap values. - * * This means that parameters can simply not contain colons or - * semi-colons. - * - * vCard 3.0 (rfc2425, rfc2426): - * * Parameters _may_ be surrounded by double quotes. - * * If this is not the case, semi-colon, colon and comma may simply not - * occur (the comma used for multiple parameter values though). - * * If it is surrounded by double-quotes, it may simply not contain - * double-quotes. - * * This means that a parameter can in no case encode double-quotes, or - * newlines. - * - * vCard 4.0 (rfc6350) - * * Behavior seems to be identical to vCard 3.0 - * - * iCalendar 2.0 (rfc5545) - * * Behavior seems to be identical to vCard 3.0 - * - * Parameter escaping mechanism (rfc6868) : - * * This rfc describes a new way to escape parameter values. - * * New-line is encoded as ^n - * * ^ is encoded as ^^. - * * " is encoded as ^' - * - * @param string $input - * @return void - */ - private function unescapeParam($input) { - - return - preg_replace_callback( - '#(\^(\^|n|\'))#', - function($matches) { - switch($matches[2]) { - case 'n' : - return "\n"; - case '^' : - return '^'; - case '\'' : - return '"'; - - // @codeCoverageIgnoreStart - } - // @codeCoverageIgnoreEnd - }, - $input - ); - } - - /** - * Gets the full quoted printable value. - * - * We need a special method for this, because newlines have both a meaning - * in vCards, and in QuotedPrintable. - * - * This method does not do any decoding. - * - * @return string - */ - private function extractQuotedPrintableValue() { - - // We need to parse the raw line again to get the start of the value. - // - // We are basically looking for the first colon (:), but we need to - // skip over the parameters first, as they may contain one. - $regex = '/^ - (?: [^:])+ # Anything but a colon - (?: "[^"]")* # A parameter in double quotes - : # start of the value we really care about - (.*)$ - /xs'; - - preg_match($regex, $this->rawLine, $matches); - - $value = $matches[1]; - // Removing the first whitespace character from every line. Kind of - // like unfolding, but we keep the newline. - $value = str_replace("\n ", "\n", $value); - - // Microsoft products don't always correctly fold lines, they may be - // missing a whitespace. So if 'forgiving' is turned on, we will take - // those as well. - if ($this->options & self::OPTION_FORGIVING) { - while(substr($value,-1) === '=') { - // Reading the line - $this->readLine(); - // Grabbing the raw form - $value.="\n" . $this->rawLine; - } - } - - return $value; - - } - -}
--- a/vendor/sabre/vobject/lib/Parser/Parser.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,77 +0,0 @@ -<?php - -namespace Sabre\VObject\Parser; - -/** - * Abstract parser. - * - * This class serves as a base-class for the different parsers. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -abstract class Parser { - - /** - * Turning on this option makes the parser more forgiving. - * - * In the case of the MimeDir parser, this means that the parser will - * accept slashes and underscores in property names, and it will also - * attempt to fix Microsoft vCard 2.1's broken line folding. - */ - const OPTION_FORGIVING = 1; - - /** - * If this option is turned on, any lines we cannot parse will be ignored - * by the reader. - */ - const OPTION_IGNORE_INVALID_LINES = 2; - - /** - * Bitmask of parser options - * - * @var int - */ - protected $options; - - /** - * Creates the parser. - * - * Optionally, it's possible to parse the input stream here. - * - * @param mixed $input - * @param int $options Any parser options (OPTION constants). - * @return void - */ - public function __construct($input = null, $options = 0) { - - if (!is_null($input)) { - $this->setInput($input); - } - $this->options = $options; - } - - /** - * This method starts the parsing process. - * - * If the input was not supplied during construction, it's possible to pass - * it here instead. - * - * If either input or options are not supplied, the defaults will be used. - * - * @param mixed $input - * @param int|null $options - * @return array - */ - abstract public function parse($input = null, $options = null); - - /** - * Sets the input data - * - * @param mixed $input - * @return void - */ - abstract public function setInput($input); - -}
--- a/vendor/sabre/vobject/lib/Property.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,518 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Property - * - * A property is always in a KEY:VALUE structure, and may optionally contain - * parameters. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -abstract class Property extends Node { - - /** - * Property name. - * - * This will contain a string such as DTSTART, SUMMARY, FN. - * - * @var string - */ - public $name; - - /** - * Property group. - * - * This is only used in vcards - * - * @var string - */ - public $group; - - /** - * List of parameters - * - * @var array - */ - public $parameters = array(); - - /** - * Current value - * - * @var mixed - */ - protected $value; - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = ';'; - - /** - * Creates the generic property. - * - * Parameters must be specified in key=>value syntax. - * - * @param Component $root The root document - * @param string $name - * @param string|array|null $value - * @param array $parameters List of parameters - * @param string $group The vcard property group - * @return void - */ - public function __construct(Component $root, $name, $value = null, array $parameters = array(), $group = null) { - - $this->name = $name; - $this->group = $group; - - $this->root = $root; - - foreach($parameters as $k=>$v) { - $this->add($k, $v); - } - - if (!is_null($value)) { - $this->setValue($value); - } - - } - - /** - * Updates the current value. - * - * This may be either a single, or multiple strings in an array. - * - * @param string|array $value - * @return void - */ - public function setValue($value) { - - $this->value = $value; - - } - - /** - * Returns the current value. - * - * This method will always return a singular value. If this was a - * multi-value object, some decision will be made first on how to represent - * it as a string. - * - * To get the correct multi-value version, use getParts. - * - * @return string - */ - public function getValue() { - - if (is_array($this->value)) { - if (count($this->value)==0) { - return null; - } elseif (count($this->value)===1) { - return $this->value[0]; - } else { - return $this->getRawMimeDirValue($this->value); - } - } else { - return $this->value; - } - - } - - /** - * Sets a multi-valued property. - * - * @param array $parts - * @return void - */ - public function setParts(array $parts) { - - $this->value = $parts; - - } - - /** - * Returns a multi-valued property. - * - * This method always returns an array, if there was only a single value, - * it will still be wrapped in an array. - * - * @return array - */ - public function getParts() { - - if (is_null($this->value)) { - return array(); - } elseif (is_array($this->value)) { - return $this->value; - } else { - return array($this->value); - } - - } - - /** - * Adds a new parameter, and returns the new item. - * - * If a parameter with same name already existed, the values will be - * combined. - * If nameless parameter is added, we try to guess it's name. - * - * @param string $name - * @param string|null|array $value - * @return Node - */ - public function add($name, $value = null) { - $noName = false; - if ($name === null) { - $name = Parameter::guessParameterNameByValue($value); - $noName = true; - } - - if (isset($this->parameters[strtoupper($name)])) { - $this->parameters[strtoupper($name)]->addValue($value); - } - else { - $param = new Parameter($this->root, $name, $value); - $param->noName = $noName; - $this->parameters[$param->name] = $param; - } - } - - /** - * Returns an iterable list of children - * - * @return array - */ - public function parameters() { - - return $this->parameters; - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - abstract public function getValueType(); - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - abstract public function setRawMimeDirValue($val); - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - abstract public function getRawMimeDirValue(); - - /** - * Turns the object back into a serialized blob. - * - * @return string - */ - public function serialize() { - - $str = $this->name; - if ($this->group) $str = $this->group . '.' . $this->name; - - foreach($this->parameters as $param) { - - $str.=';' . $param->serialize(); - - } - - $str.=':' . $this->getRawMimeDirValue(); - - $out = ''; - while(strlen($str)>0) { - if (strlen($str)>75) { - $out.= mb_strcut($str,0,75,'utf-8') . "\r\n"; - $str = ' ' . mb_strcut($str,75,strlen($str),'utf-8'); - } else { - $out.=$str . "\r\n"; - $str=''; - break; - } - } - - return $out; - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - return $this->getParts(); - - } - - /** - * Sets the json value, as it would appear in a jCard or jCal object. - * - * The value must always be an array. - * - * @param array $value - * @return void - */ - public function setJsonValue(array $value) { - - if (count($value)===1) { - $this->setValue(reset($value)); - } else { - $this->setValue($value); - } - - } - - /** - * This method returns an array, with the representation as it should be - * encoded in json. This is used to create jCard or jCal documents. - * - * @return array - */ - public function jsonSerialize() { - - $parameters = array(); - - foreach($this->parameters as $parameter) { - if ($parameter->name === 'VALUE') { - continue; - } - $parameters[strtolower($parameter->name)] = $parameter->jsonSerialize(); - } - // In jCard, we need to encode the property-group as a separate 'group' - // parameter. - if ($this->group) { - $parameters['group'] = $this->group; - } - - return array_merge( - array( - strtolower($this->name), - (object)$parameters, - strtolower($this->getValueType()), - ), - $this->getJsonValue() - ); - } - - - /** - * Called when this object is being cast to a string. - * - * If the property only had a single value, you will get just that. In the - * case the property had multiple values, the contents will be escaped and - * combined with ,. - * - * @return string - */ - public function __toString() { - - return (string)$this->getValue(); - - } - - /* ArrayAccess interface {{{ */ - - /** - * Checks if an array element exists - * - * @param mixed $name - * @return bool - */ - public function offsetExists($name) { - - if (is_int($name)) return parent::offsetExists($name); - - $name = strtoupper($name); - - foreach($this->parameters as $parameter) { - if ($parameter->name == $name) return true; - } - return false; - - } - - /** - * Returns a parameter. - * - * If the parameter does not exist, null is returned. - * - * @param string $name - * @return Node - */ - public function offsetGet($name) { - - if (is_int($name)) return parent::offsetGet($name); - $name = strtoupper($name); - - if (!isset($this->parameters[$name])) { - return null; - } - - return $this->parameters[$name]; - - } - - /** - * Creates a new parameter - * - * @param string $name - * @param mixed $value - * @return void - */ - public function offsetSet($name, $value) { - - if (is_int($name)) { - parent::offsetSet($name, $value); - // @codeCoverageIgnoreStart - // This will never be reached, because an exception is always - // thrown. - return; - // @codeCoverageIgnoreEnd - } - - $param = new Parameter($this->root, $name, $value); - $this->parameters[$param->name] = $param; - - } - - /** - * Removes one or more parameters with the specified name - * - * @param string $name - * @return void - */ - public function offsetUnset($name) { - - if (is_int($name)) { - parent::offsetUnset($name); - // @codeCoverageIgnoreStart - // This will never be reached, because an exception is always - // thrown. - return; - // @codeCoverageIgnoreEnd - } - - unset($this->parameters[strtoupper($name)]); - - } - /* }}} */ - - /** - * This method is automatically called when the object is cloned. - * Specifically, this will ensure all child elements are also cloned. - * - * @return void - */ - public function __clone() { - - foreach($this->parameters as $key=>$child) { - $this->parameters[$key] = clone $child; - $this->parameters[$key]->parent = $this; - } - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * - Node::REPAIR - If something is broken, and automatic repair may - * be attempted. - * - * An array is returned with warnings. - * - * Every item in the array has the following properties: - * * level - (number between 1 and 3 with severity information) - * * message - (human readable message) - * * node - (reference to the offending node) - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - $warnings = array(); - - // Checking if our value is UTF-8 - if (!StringUtil::isUTF8($this->getRawMimeDirValue())) { - - $oldValue = $this->getRawMimeDirValue(); - $level = 3; - if ($options & self::REPAIR) { - $newValue = StringUtil::convertToUTF8($oldValue); - if (true || StringUtil::isUTF8($newValue)) { - $this->setRawMimeDirValue($newValue); - $level = 1; - } - - } - - - if (preg_match('%([\x00-\x08\x0B-\x0C\x0E-\x1F\x7F])%', $oldValue, $matches)) { - $message = 'Property contained a control character (0x' . bin2hex($matches[1]) . ')'; - } else { - $message = 'Property is not valid UTF-8! ' . $oldValue; - } - - $warnings[] = array( - 'level' => $level, - 'message' => $message, - 'node' => $this, - ); - } - - // Checking if the propertyname does not contain any invalid bytes. - if (!preg_match('/^([A-Z0-9-]+)$/', $this->name)) { - $warnings[] = array( - 'level' => 1, - 'message' => 'The propertyname: ' . $this->name . ' contains invalid characters. Only A-Z, 0-9 and - are allowed', - 'node' => $this, - ); - if ($options & self::REPAIR) { - // Uppercasing and converting underscores to dashes. - $this->name = strtoupper( - str_replace('_', '-', $this->name) - ); - // Removing every other invalid character - $this->name = preg_replace('/([^A-Z0-9-])/u', '', $this->name); - - } - - } - - // Validating inner parameters - foreach($this->parameters as $param) { - $warnings = array_merge($warnings, $param->validate($options)); - } - - return $warnings; - - } - -}
--- a/vendor/sabre/vobject/lib/Property/Binary.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,127 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use - LogicException, - Sabre\VObject\Property; - -/** - * BINARY property - * - * This object represents BINARY values. - * - * Binary values are most commonly used by the iCalendar ATTACH property, and - * the vCard PHOTO property. - * - * This property will transparently encode and decode to base64. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Binary extends Property { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = null; - - /** - * Updates the current value. - * - * This may be either a single, or multiple strings in an array. - * - * @param string|array $value - * @return void - */ - public function setValue($value) { - - if(is_array($value)) { - - if(count($value) === 1) { - $this->value = $value[0]; - } else { - throw new \InvalidArgumentException('The argument must either be a string or an array with only one child'); - } - - } else { - - $this->value = $value; - - } - - } - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $this->value = base64_decode($val); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return base64_encode($this->value); - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return 'BINARY'; - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - return array(base64_encode($this->getValue())); - - } - - /** - * Sets the json value, as it would appear in a jCard or jCal object. - * - * The value must always be an array. - * - * @param array $value - * @return void - */ - public function setJsonValue(array $value) { - - $value = array_map('base64_decode', $value); - parent::setJsonValue($value); - - } - -}
--- a/vendor/sabre/vobject/lib/Property/Boolean.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,63 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use - Sabre\VObject\Property; - -/** - * Boolean property - * - * This object represents BOOLEAN values. These are always the case-insenstive - * string TRUE or FALSE. - * - * Automatic conversion to PHP's true and false are done. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Boolean extends Property { - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $val = strtoupper($val)==='TRUE'?true:false; - $this->setValue($val); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return $this->value?'TRUE':'FALSE'; - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return 'BOOLEAN'; - - } - -}
--- a/vendor/sabre/vobject/lib/Property/FlatText.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,49 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -/** - * FlatText property - * - * This object represents certain TEXT values. - * - * Specifically, this property is used for text values where there is only 1 - * part. Semi-colons and colons will be de-escaped when deserializing, but if - * any semi-colons or commas appear without a backslash, we will not assume - * that they are delimiters. - * - * vCard 2.1 specifically has a whole bunch of properties where this may - * happen, as it only defines a delimiter for a few properties. - * - * vCard 4.0 states something similar. An unescaped semi-colon _may_ be a - * delimiter, depending on the property. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class FlatText extends Text { - - /** - * Field separator - * - * @var string - */ - public $delimiter = ','; - - /** - * Sets the value as a quoted-printable encoded string. - * - * Overriding this so we're not splitting on a ; delimiter. - * - * @param string $val - * @return void - */ - public function setQuotedPrintableValue($val) { - - $val = quoted_printable_decode($val); - $this->setValue($val); - - } - -}
--- a/vendor/sabre/vobject/lib/Property/Float.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,104 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use - Sabre\VObject\Property; - -/** - * Float property - * - * This object represents FLOAT values. These can be 1 or more floating-point - * numbers. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Float extends Property { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = ';'; - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $val = explode($this->delimiter, $val); - foreach($val as &$item) { - $item = (float)$item; - } - $this->setParts($val); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return implode( - $this->delimiter, - $this->getParts() - ); - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "FLOAT"; - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - $val = array_map( - function($item) { - - return (float)$item; - - }, - $this->getParts() - ); - - // Special-casing the GEO property. - // - // See: - // http://tools.ietf.org/html/draft-ietf-jcardcal-jcal-04#section-3.4.1.2 - if ($this->name==='GEO') { - return array($val); - } else { - return $val; - } - - } -}
--- a/vendor/sabre/vobject/lib/Property/ICalendar/CalAddress.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,61 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -use - Sabre\VObject\Property\Text; - -/** - * CalAddress property - * - * This object encodes CAL-ADDRESS values, as defined in rfc5545 - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class CalAddress extends Text { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = null; - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return 'CAL-ADDRESS'; - - } - - /** - * This returns a normalized form of the value. - * - * This is primarily used right now to turn mixed-cased schemes in user - * uris to lower-case. - * - * Evolution in particular tends to encode mailto: as MAILTO:. - * - * @return string - */ - public function getNormalizedValue() { - - $input = $this->getValue(); - if (!strpos($input, ':')) { - return $input; - } - list($schema, $everythingElse) = explode(':', $input, 2); - return strtolower($schema) . ':' . $everythingElse; - - } -}
--- a/vendor/sabre/vobject/lib/Property/ICalendar/Date.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,18 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -/** - * DateTime property - * - * This object represents DATE values, as defined here: - * - * http://tools.ietf.org/html/rfc5545#section-3.3.5 - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Date extends DateTime { - -}
--- a/vendor/sabre/vobject/lib/Property/ICalendar/DateTime.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,388 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -use DateTimeZone; -use Sabre\VObject\Property; -use Sabre\VObject\DateTimeParser; -use Sabre\VObject\TimeZoneUtil; - -/** - * DateTime property - * - * This object represents DATE-TIME values, as defined here: - * - * http://tools.ietf.org/html/rfc5545#section-3.3.4 - * - * This particular object has a bit of hackish magic that it may also in some - * cases represent a DATE value. This is because it's a common usecase to be - * able to change a DATE-TIME into a DATE. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class DateTime extends Property { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = ','; - - /** - * Sets a multi-valued property. - * - * You may also specify DateTime objects here. - * - * @param array $parts - * @return void - */ - public function setParts(array $parts) { - - if (isset($parts[0]) && $parts[0] instanceof \DateTime) { - $this->setDateTimes($parts); - } else { - parent::setParts($parts); - } - - } - - /** - * Updates the current value. - * - * This may be either a single, or multiple strings in an array. - * - * Instead of strings, you may also use DateTime here. - * - * @param string|array|\DateTime $value - * @return void - */ - public function setValue($value) { - - if (is_array($value) && isset($value[0]) && $value[0] instanceof \DateTime) { - $this->setDateTimes($value); - } elseif ($value instanceof \DateTime) { - $this->setDateTimes(array($value)); - } else { - parent::setValue($value); - } - - } - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $this->setValue(explode($this->delimiter, $val)); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return implode($this->delimiter, $this->getParts()); - - } - - /** - * Returns true if this is a DATE-TIME value, false if it's a DATE. - * - * @return bool - */ - public function hasTime() { - - return strtoupper((string)$this['VALUE']) !== 'DATE'; - - } - - /** - * Returns true if this is a floating DATE or DATE-TIME. - * - * Note that DATE is always floating. - */ - public function isFloating() { - - return - !$this->hasTime() || - ( - !isset($this['TZID']) && - strpos($this->getValue(),'Z')===false - ); - - } - - /** - * Returns a date-time value. - * - * Note that if this property contained more than 1 date-time, only the - * first will be returned. To get an array with multiple values, call - * getDateTimes. - * - * If no timezone information is known, because it's either an all-day - * property or floating time, we will use the DateTimeZone argument to - * figure out the exact date. - * - * @param DateTimeZone $timeZone - * @return \DateTime - */ - public function getDateTime(DateTimeZone $timeZone = null) { - - $dt = $this->getDateTimes($timeZone); - if (!$dt) return null; - - return $dt[0]; - - } - - /** - * Returns multiple date-time values. - * - * If no timezone information is known, because it's either an all-day - * property or floating time, we will use the DateTimeZone argument to - * figure out the exact date. - * - * @param DateTimeZone $timeZone - * @return \DateTime[] - */ - public function getDateTimes(DateTimeZone $timeZone = null) { - - // Does the property have a TZID? - $tzid = $this['TZID']; - - if ($tzid) { - $timeZone = TimeZoneUtil::getTimeZone((string)$tzid, $this->root); - } - - $dts = array(); - foreach($this->getParts() as $part) { - $dts[] = DateTimeParser::parse($part, $timeZone); - } - return $dts; - - } - - /** - * Sets the property as a DateTime object. - * - * @param \DateTime $dt - * @param bool isFloating If set to true, timezones will be ignored. - * @return void - */ - public function setDateTime(\DateTime $dt, $isFloating = false) { - - $this->setDateTimes(array($dt), $isFloating); - - } - - /** - * Sets the property as multiple date-time objects. - * - * The first value will be used as a reference for the timezones, and all - * the otehr values will be adjusted for that timezone - * - * @param \DateTime[] $dt - * @param bool isFloating If set to true, timezones will be ignored. - * @return void - */ - public function setDateTimes(array $dt, $isFloating = false) { - - $values = array(); - - if($this->hasTime()) { - - $tz = null; - $isUtc = false; - - foreach($dt as $d) { - - if ($isFloating) { - $values[] = $d->format('Ymd\\THis'); - continue; - } - if (is_null($tz)) { - $tz = $d->getTimeZone(); - $isUtc = in_array($tz->getName() , array('UTC', 'GMT', 'Z')); - if (!$isUtc) { - $this->offsetSet('TZID', $tz->getName()); - } - } else { - $d->setTimeZone($tz); - } - - if ($isUtc) { - $values[] = $d->format('Ymd\\THis\\Z'); - } else { - $values[] = $d->format('Ymd\\THis'); - } - - } - if ($isUtc || $isFloating) { - $this->offsetUnset('TZID'); - } - - } else { - - foreach($dt as $d) { - - $values[] = $d->format('Ymd'); - - } - $this->offsetUnset('TZID'); - - } - - $this->value = $values; - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return $this->hasTime()?'DATE-TIME':'DATE'; - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - $dts = $this->getDateTimes(); - $hasTime = $this->hasTime(); - $isFloating = $this->isFloating(); - - $tz = $dts[0]->getTimeZone(); - $isUtc = $isFloating ? false : in_array($tz->getName() , array('UTC', 'GMT', 'Z')); - - return array_map( - function($dt) use ($hasTime, $isUtc) { - - if ($hasTime) { - return $dt->format('Y-m-d\\TH:i:s') . ($isUtc?'Z':''); - } else { - return $dt->format('Y-m-d'); - } - - }, - $dts - ); - - } - - /** - * Sets the json value, as it would appear in a jCard or jCal object. - * - * The value must always be an array. - * - * @param array $value - * @return void - */ - public function setJsonValue(array $value) { - - // dates and times in jCal have one difference to dates and times in - // iCalendar. In jCal date-parts are separated by dashes, and - // time-parts are separated by colons. It makes sense to just remove - // those. - $this->setValue( - array_map( - function($item) { - - return strtr($item, array(':'=>'', '-'=>'')); - - }, - $value - ) - ); - - } - /** - * We need to intercept offsetSet, because it may be used to alter the - * VALUE from DATE-TIME to DATE or vice-versa. - * - * @param string $name - * @param mixed $value - * @return void - */ - public function offsetSet($name, $value) { - - parent::offsetSet($name, $value); - if (strtoupper($name)!=='VALUE') { - return; - } - - // This will ensure that dates are correctly encoded. - $this->setDateTimes($this->getDateTimes()); - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * Node::REPAIR - May attempt to automatically repair the problem. - * - * This method returns an array with detected problems. - * Every element has the following properties: - * - * * level - problem level. - * * message - A human-readable string describing the issue. - * * node - A reference to the problematic node. - * - * The level means: - * 1 - The issue was repaired (only happens if REPAIR was turned on) - * 2 - An inconsequential issue - * 3 - A severe issue. - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - $messages = parent::validate($options); - $valueType = $this->getValueType(); - $value = $this->getValue(); - try { - switch($valueType) { - case 'DATE' : - $foo = DateTimeParser::parseDate($value); - break; - case 'DATE-TIME' : - $foo = DateTimeParser::parseDateTime($value); - break; - } - } catch (\LogicException $e) { - $messages[] = array( - 'level' => 3, - 'message' => 'The supplied value (' . $value . ') is not a correct ' . $valueType, - 'node' => $this, - ); - } - return $messages; - - } -}
--- a/vendor/sabre/vobject/lib/Property/ICalendar/Duration.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,86 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -use - Sabre\VObject\Property, - Sabre\VObject\Parser\MimeDir, - Sabre\VObject\DateTimeParser; - -/** - * Duration property - * - * This object represents DURATION values, as defined here: - * - * http://tools.ietf.org/html/rfc5545#section-3.3.6 - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Duration extends Property { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = ','; - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $this->setValue(explode($this->delimiter, $val)); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return implode($this->delimiter, $this->getParts()); - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return 'DURATION'; - - } - - /** - * Returns a DateInterval representation of the Duration property. - * - * If the property has more than one value, only the first is returned. - * - * @return \DateInterval - */ - public function getDateInterval() { - - $parts = $this->getParts(); - $value = $parts[0]; - return DateTimeParser::parseDuration($value); - - } - -}
--- a/vendor/sabre/vobject/lib/Property/ICalendar/Period.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,129 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -use - Sabre\VObject\Property, - Sabre\VObject\Parser\MimeDir, - Sabre\VObject\DateTimeParser; - -/** - * Period property - * - * This object represents PERIOD values, as defined here: - * - * http://tools.ietf.org/html/rfc5545#section-3.8.2.6 - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Period extends Property { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = ','; - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $this->setValue(explode($this->delimiter, $val)); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return implode($this->delimiter, $this->getParts()); - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "PERIOD"; - - } - - /** - * Sets the json value, as it would appear in a jCard or jCal object. - * - * The value must always be an array. - * - * @param array $value - * @return void - */ - public function setJsonValue(array $value) { - - $value = array_map( - function($item) { - - return strtr(implode('/', $item), array(':' => '', '-' => '')); - - }, - $value - ); - parent::setJsonValue($value); - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - $return = array(); - foreach($this->getParts() as $item) { - - list($start, $end) = explode('/', $item, 2); - - $start = DateTimeParser::parseDateTime($start); - - // This is a duration value. - if ($end[0]==='P') { - $return[] = array( - $start->format('Y-m-d\\TH:i:s'), - $end - ); - } else { - $end = DateTimeParser::parseDateTime($end); - $return[] = array( - $start->format('Y-m-d\\TH:i:s'), - $end->format('Y-m-d\\TH:i:s'), - ); - } - - } - - return $return; - - } - -}
--- a/vendor/sabre/vobject/lib/Property/ICalendar/Recur.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,203 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -use - Sabre\VObject\Property, - Sabre\VObject\Parser\MimeDir; - -/** - * Recur property - * - * This object represents RECUR properties. - * These values are just used for RRULE and the now deprecated EXRULE. - * - * The RRULE property may look something like this: - * - * RRULE:FREQ=MONTHLY;BYDAY=1,2,3;BYHOUR=5. - * - * This property exposes this as a key=>value array that is accessible using - * getParts, and may be set using setParts. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Recur extends Property { - - /** - * Updates the current value. - * - * This may be either a single, or multiple strings in an array. - * - * @param string|array $value - * @return void - */ - public function setValue($value) { - - // If we're getting the data from json, we'll be receiving an object - if ($value instanceof \StdClass) { - $value = (array)$value; - } - - if (is_array($value)) { - $newVal = array(); - foreach($value as $k=>$v) { - - if (is_string($v)) { - $v = strtoupper($v); - - // The value had multiple sub-values - if (strpos($v,',')!==false) { - $v = explode(',', $v); - } - } else { - $v = array_map('strtoupper', $v); - } - - $newVal[strtoupper($k)] = $v; - } - $this->value = $newVal; - } elseif (is_string($value)) { - $this->value = self::stringToArray($value); - } else { - throw new \InvalidArgumentException('You must either pass a string, or a key=>value array'); - } - - } - - /** - * Returns the current value. - * - * This method will always return a singular value. If this was a - * multi-value object, some decision will be made first on how to represent - * it as a string. - * - * To get the correct multi-value version, use getParts. - * - * @return string - */ - public function getValue() { - - $out = array(); - foreach($this->value as $key=>$value) { - $out[] = $key . '=' . (is_array($value)?implode(',', $value):$value); - } - return strtoupper(implode(';',$out)); - - } - - /** - * Sets a multi-valued property. - * - * @param array $parts - * @return void - */ - public function setParts(array $parts) { - - $this->setValue($parts); - - } - - /** - * Returns a multi-valued property. - * - * This method always returns an array, if there was only a single value, - * it will still be wrapped in an array. - * - * @return array - */ - public function getParts() { - - return $this->value; - - } - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $this->setValue($val); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return $this->getValue(); - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "RECUR"; - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - $values = array(); - foreach($this->getParts() as $k=>$v) { - $values[strtolower($k)] = $v; - } - return array($values); - - } - - /** - * Parses an RRULE value string, and turns it into a struct-ish array. - * - * @param string $value - * @return array - */ - static function stringToArray($value) { - - $value = strtoupper($value); - $newValue = array(); - foreach(explode(';', $value) as $part) { - - // Skipping empty parts. - if (empty($part)) { - continue; - } - list($partName, $partValue) = explode('=', $part); - - // The value itself had multiple values.. - if (strpos($partValue,',')!==false) { - $partValue=explode(',', $partValue); - } - $newValue[$partName] = $partValue; - - } - - return $newValue; - - } - -}
--- a/vendor/sabre/vobject/lib/Property/Integer.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,72 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use - Sabre\VObject\Property; - -/** - * Integer property - * - * This object represents INTEGER values. These are always a single integer. - * They may be preceeded by either + or -. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Integer extends Property { - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $this->setValue((int)$val); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return $this->value; - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "INTEGER"; - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - return array((int)$this->getValue()); - - } -}
--- a/vendor/sabre/vobject/lib/Property/Text.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,333 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use - Sabre\VObject\Property, - Sabre\VObject\Component, - Sabre\VObject\Parser\MimeDir, - Sabre\VObject\Document; - -/** - * Text property - * - * This object represents TEXT values. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Text extends Property { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string - */ - public $delimiter = ','; - - /** - * List of properties that are considered 'structured'. - * - * @var array - */ - protected $structuredValues = array( - // vCard - 'N', - 'ADR', - 'ORG', - 'GENDER', - - // iCalendar - 'REQUEST-STATUS', - ); - - /** - * Some text components have a minimum number of components. - * - * N must for instance be represented as 5 components, separated by ;, even - * if the last few components are unused. - * - * @var array - */ - protected $minimumPropertyValues = array( - 'N' => 5, - 'ADR' => 7, - ); - - /** - * Creates the property. - * - * You can specify the parameters either in key=>value syntax, in which case - * parameters will automatically be created, or you can just pass a list of - * Parameter objects. - * - * @param Component $root The root document - * @param string $name - * @param string|array|null $value - * @param array $parameters List of parameters - * @param string $group The vcard property group - * @return void - */ - public function __construct(Component $root, $name, $value = null, array $parameters = array(), $group = null) { - - // There's two types of multi-valued text properties: - // 1. multivalue properties. - // 2. structured value properties - // - // The former is always separated by a comma, the latter by semi-colon. - if (in_array($name, $this->structuredValues)) { - $this->delimiter = ';'; - } - - parent::__construct($root, $name, $value, $parameters, $group); - - } - - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $this->setValue(MimeDir::unescapeValue($val, $this->delimiter)); - - } - - /** - * Sets the value as a quoted-printable encoded string. - * - * @param string $val - * @return void - */ - public function setQuotedPrintableValue($val) { - - $val = quoted_printable_decode($val); - - // Quoted printable only appears in vCard 2.1, and the only character - // that may be escaped there is ;. So we are simply splitting on just - // that. - // - // We also don't have to unescape \\, so all we need to look for is a ; - // that's not preceeded with a \. - $regex = '# (?<!\\\\) ; #x'; - $matches = preg_split($regex, $val); - $this->setValue($matches); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - $val = $this->getParts(); - - if (isset($this->minimumPropertyValues[$this->name])) { - $val = array_pad($val, $this->minimumPropertyValues[$this->name], ''); - } - - foreach($val as &$item) { - - if (!is_array($item)) { - $item = array($item); - } - - foreach($item as &$subItem) { - $subItem = strtr( - $subItem, - array( - '\\' => '\\\\', - ';' => '\;', - ',' => '\,', - "\n" => '\n', - "\r" => "", - ) - ); - } - $item = implode(',', $item); - - } - - return implode($this->delimiter, $val); - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - // Structured text values should always be returned as a single - // array-item. Multi-value text should be returned as multiple items in - // the top-array. - if (in_array($this->name, $this->structuredValues)) { - return array($this->getParts()); - } else { - return $this->getParts(); - } - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "TEXT"; - - } - - /** - * Turns the object back into a serialized blob. - * - * @return string - */ - public function serialize() { - - // We need to kick in a special type of encoding, if it's a 2.1 vcard. - if ($this->root->getDocumentType() !== Document::VCARD21) { - return parent::serialize(); - } - - $val = $this->getParts(); - - if (isset($this->minimumPropertyValues[$this->name])) { - $val = array_pad($val, $this->minimumPropertyValues[$this->name], ''); - } - - // Imploding multiple parts into a single value, and splitting the - // values with ;. - if (count($val)>1) { - foreach($val as $k=>$v) { - $val[$k] = str_replace(';','\;', $v); - } - $val = implode(';', $val); - } else { - $val = $val[0]; - } - - $str = $this->name; - if ($this->group) $str = $this->group . '.' . $this->name; - foreach($this->parameters as $param) { - - if ($param->getValue() === 'QUOTED-PRINTABLE') { - continue; - } - $str.=';' . $param->serialize(); - - } - - - - // If the resulting value contains a \n, we must encode it as - // quoted-printable. - if (strpos($val,"\n") !== false) { - - $str.=';ENCODING=QUOTED-PRINTABLE:'; - $lastLine=$str; - $out = null; - - // The PHP built-in quoted-printable-encode does not correctly - // encode newlines for us. Specifically, the \r\n sequence must in - // vcards be encoded as =0D=OA and we must insert soft-newlines - // every 75 bytes. - for($ii=0;$ii<strlen($val);$ii++) { - $ord = ord($val[$ii]); - // These characters are encoded as themselves. - if ($ord >= 32 && $ord <=126) { - $lastLine.=$val[$ii]; - } else { - $lastLine.='=' . strtoupper(bin2hex($val[$ii])); - } - if (strlen($lastLine)>=75) { - // Soft line break - $out.=$lastLine. "=\r\n "; - $lastLine = null; - } - - } - if (!is_null($lastLine)) $out.= $lastLine . "\r\n"; - return $out; - - } else { - $str.=':' . $val; - $out = ''; - while(strlen($str)>0) { - if (strlen($str)>75) { - $out.= mb_strcut($str,0,75,'utf-8') . "\r\n"; - $str = ' ' . mb_strcut($str,75,strlen($str),'utf-8'); - } else { - $out.=$str . "\r\n"; - $str=''; - break; - } - } - - return $out; - - - } - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * - Node::REPAIR - If something is broken, and automatic repair may - * be attempted. - * - * An array is returned with warnings. - * - * Every item in the array has the following properties: - * * level - (number between 1 and 3 with severity information) - * * message - (human readable message) - * * node - (reference to the offending node) - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - $warnings = parent::validate($options); - - if (isset($this->minimumPropertyValues[$this->name])) { - - $minimum = $this->minimumPropertyValues[$this->name]; - $parts = $this->getParts(); - if (count($parts) < $minimum) { - $warnings[] = array( - 'level' => 1, - 'message' => 'This property must have at least ' . $minimum . ' components. It only has ' . count($parts), - 'node' => $this, - ); - if ($options & self::REPAIR) { - $parts = array_pad($parts, $minimum, ''); - $this->setParts($parts); - } - } - - } - return $warnings; - - } -}
--- a/vendor/sabre/vobject/lib/Property/Time.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,94 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject\DateTimeParser; - -/** - * Time property - * - * This object encodes TIME values. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Time extends Text { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = null; - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "TIME"; - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - $parts = DateTimeParser::parseVCardTime($this->getValue()); - - $timeStr = ''; - - // Hour - if (!is_null($parts['hour'])) { - $timeStr.=$parts['hour']; - - if (!is_null($parts['minute'])) { - $timeStr.=':'; - } - } else { - // We know either minute or second _must_ be set, so we insert a - // dash for an empty value. - $timeStr.='-'; - } - - // Minute - if (!is_null($parts['minute'])) { - $timeStr.=$parts['minute']; - - if (!is_null($parts['second'])) { - $timeStr.=':'; - } - } else { - if (isset($parts['second'])) { - // Dash for empty minute - $timeStr.='-'; - } - } - - // Second - if (!is_null($parts['second'])) { - $timeStr.=$parts['second']; - } - - // Timezone - if (!is_null($parts['timezone'])) { - $timeStr.=$parts['timezone']; - } - - return array($timeStr); - - } - -}
--- a/vendor/sabre/vobject/lib/Property/Unknown.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,50 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use - Sabre\VObject\Property, - Sabre\VObject\Component, - Sabre\VObject\Parser\MimeDir, - Sabre\VObject\Document; - -/** - * Unknown property - * - * This object represents any properties not recognized by the parser. - * This type of value has been introduced by the jCal, jCard specs. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Unknown extends Text { - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - return array($this->getRawMimeDirValue()); - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "UNKNOWN"; - - } - -}
--- a/vendor/sabre/vobject/lib/Property/Uri.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,95 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject\Property; - -/** - * URI property - * - * This object encodes URI values. vCard 2.1 calls these URL. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Uri extends Text { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = null; - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "URI"; - - } - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - // Normally we don't need to do any type of unescaping for these - // properties, however.. we've noticed that Google Contacts - // specifically escapes the colon (:) with a blackslash. While I have - // no clue why they thought that was a good idea, I'm unescaping it - // anyway. - // - // Good thing backslashes are not allowed in urls. Makes it easy to - // assume that a backslash is always intended as an escape character. - if ($this->name === 'URL') { - $regex = '# (?: (\\\\ (?: \\\\ | : ) ) ) #x'; - $matches = preg_split($regex, $val, -1, PREG_SPLIT_DELIM_CAPTURE | PREG_SPLIT_NO_EMPTY); - $newVal = ''; - foreach($matches as $match) { - switch($match) { - case '\:' : - $newVal.=':'; - break; - default : - $newVal.=$match; - break; - } - } - $this->value = $newVal; - } else { - $this->value = $val; - } - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - if (is_array($this->value)) { - return $this->value[0]; - } else { - return $this->value; - } - - } - -}
--- a/vendor/sabre/vobject/lib/Property/UtcOffset.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,37 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -/** - * UtcOffset property - * - * This object encodes UTC-OFFSET values. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class UtcOffset extends Text { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = null; - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "UTC-OFFSET"; - - } -}
--- a/vendor/sabre/vobject/lib/Property/VCard/Date.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,33 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\VCard; - -use - Sabre\VObject\DateTimeParser; - -/** - * Date property - * - * This object encodes vCard DATE values. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Date extends DateAndOrTime { - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "DATE"; - - } - -}
--- a/vendor/sabre/vobject/lib/Property/VCard/DateAndOrTime.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,317 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\VCard; - -use - Sabre\VObject\DateTimeParser, - Sabre\VObject\Property\Text, - Sabre\VObject\Property, - DateTime; - -/** - * DateAndOrTime property - * - * This object encodes DATE-AND-OR-TIME values. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class DateAndOrTime extends Property { - - /** - * Field separator - * - * @var null|string - */ - public $delimiter = null; - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "DATE-AND-OR-TIME"; - - } - - /** - * Sets a multi-valued property. - * - * You may also specify DateTime objects here. - * - * @param array $parts - * @return void - */ - public function setParts(array $parts) { - - if (count($parts)>1) { - throw new \InvalidArgumentException('Only one value allowed'); - } - if (isset($parts[0]) && $parts[0] instanceof \DateTime) { - $this->setDateTime($parts[0]); - } else { - parent::setParts($parts); - } - - } - - /** - * Updates the current value. - * - * This may be either a single, or multiple strings in an array. - * - * Instead of strings, you may also use DateTime here. - * - * @param string|array|\DateTime $value - * @return void - */ - public function setValue($value) { - - if ($value instanceof \DateTime) { - $this->setDateTime($value); - } else { - parent::setValue($value); - } - - } - - /** - * Sets the property as a DateTime object. - * - * @param \DateTime $dt - * @return void - */ - public function setDateTime(\DateTime $dt) { - - $values = array(); - - $tz = null; - $isUtc = false; - - $tz = $dt->getTimeZone(); - $isUtc = in_array($tz->getName() , array('UTC', 'GMT', 'Z')); - - if ($isUtc) { - $value = $dt->format('Ymd\\THis\\Z'); - } else { - // Calculating the offset. - $value = $dt->format('Ymd\\THisO'); - } - - $this->value = $value; - - } - - /** - * Returns a date-time value. - * - * Note that if this property contained more than 1 date-time, only the - * first will be returned. To get an array with multiple values, call - * getDateTimes. - * - * If no time was specified, we will always use midnight (in the default - * timezone) as the time. - * - * If parts of the date were omitted, such as the year, we will grab the - * current values for those. So at the time of writing, if the year was - * omitted, we would have filled in 2014. - * - * @return \DateTime - */ - public function getDateTime() { - - $dts = array(); - $now = new DateTime(); - - $tzFormat = $now->getTimezone()->getOffset($now)===0?'\\Z':'O'; - $nowParts = DateTimeParser::parseVCardDateTime($now->format('Ymd\\This' . $tzFormat)); - - $value = $this->getValue(); - - $dateParts = DateTimeParser::parseVCardDateTime($this->getValue()); - - // This sets all the missing parts to the current date/time. - // So if the year was missing for a birthday, we're making it 'this - // year'. - foreach($dateParts as $k=>$v) { - if (is_null($v)) { - $dateParts[$k] = $nowParts[$k]; - } - } - return new DateTime("$dateParts[year]-$dateParts[month]-$dateParts[date] $dateParts[hour]:$dateParts[minute]:$dateParts[second] $dateParts[timezone]"); - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - $parts = DateTimeParser::parseVCardDateTime($this->getValue()); - - $dateStr = ''; - - // Year - if (!is_null($parts['year'])) { - $dateStr.=$parts['year']; - - if (!is_null($parts['month'])) { - // If a year and a month is set, we need to insert a separator - // dash. - $dateStr.='-'; - } - - } else { - - if (!is_null($parts['month']) || !is_null($parts['date'])) { - // Inserting two dashes - $dateStr.='--'; - } - - } - - // Month - - if (!is_null($parts['month'])) { - $dateStr.=$parts['month']; - - if (isset($parts['date'])) { - // If month and date are set, we need the separator dash. - $dateStr.='-'; - } - } else { - if (isset($parts['date'])) { - // If the month is empty, and a date is set, we need a 'empty - // dash' - $dateStr.='-'; - } - } - - // Date - if (!is_null($parts['date'])) { - $dateStr.=$parts['date']; - } - - - // Early exit if we don't have a time string. - if (is_null($parts['hour']) && is_null($parts['minute']) && is_null($parts['second'])) { - return array($dateStr); - } - - $dateStr.='T'; - - // Hour - if (!is_null($parts['hour'])) { - $dateStr.=$parts['hour']; - - if (!is_null($parts['minute'])) { - $dateStr.=':'; - } - } else { - // We know either minute or second _must_ be set, so we insert a - // dash for an empty value. - $dateStr.='-'; - } - - // Minute - if (!is_null($parts['minute'])) { - $dateStr.=$parts['minute']; - - if (!is_null($parts['second'])) { - $dateStr.=':'; - } - } else { - if (isset($parts['second'])) { - // Dash for empty minute - $dateStr.='-'; - } - } - - // Second - if (!is_null($parts['second'])) { - $dateStr.=$parts['second']; - } - - // Timezone - if (!is_null($parts['timezone'])) { - $dateStr.=$parts['timezone']; - } - - return array($dateStr); - - } - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $this->setValue($val); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return implode($this->delimiter, $this->getParts()); - - } - - /** - * Validates the node for correctness. - * - * The following options are supported: - * Node::REPAIR - May attempt to automatically repair the problem. - * - * This method returns an array with detected problems. - * Every element has the following properties: - * - * * level - problem level. - * * message - A human-readable string describing the issue. - * * node - A reference to the problematic node. - * - * The level means: - * 1 - The issue was repaired (only happens if REPAIR was turned on) - * 2 - An inconsequential issue - * 3 - A severe issue. - * - * @param int $options - * @return array - */ - public function validate($options = 0) { - - $messages = parent::validate($options); - $value = $this->getValue(); - try { - DateTimeParser::parseVCardDateTime($value); - } catch (\InvalidArgumentException $e) { - $messages[] = array( - 'level' => 3, - 'message' => 'The supplied value (' . $value . ') is not a correct DATE-AND-OR-TIME property', - 'node' => $this, - ); - } - return $messages; - - } -}
--- a/vendor/sabre/vobject/lib/Property/VCard/DateTime.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,33 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\VCard; - -use - Sabre\VObject\DateTimeParser; - -/** - * DateTime property - * - * This object encodes DATE-TIME values for vCards. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class DateTime extends DateAndOrTime { - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "DATE-TIME"; - - } - -}
--- a/vendor/sabre/vobject/lib/Property/VCard/LanguageTag.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,59 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\VCard; - -use - Sabre\VObject\Property; - -/** - * LanguageTag property - * - * This object represents LANGUAGE-TAG values as used in vCards. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class LanguageTag extends Property { - - /** - * Sets a raw value coming from a mimedir (iCalendar/vCard) file. - * - * This has been 'unfolded', so only 1 line will be passed. Unescaping is - * not yet done, but parameters are not included. - * - * @param string $val - * @return void - */ - public function setRawMimeDirValue($val) { - - $this->setValue($val); - - } - - /** - * Returns a raw mime-dir representation of the value. - * - * @return string - */ - public function getRawMimeDirValue() { - - return $this->value; - - } - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "LANGUAGE-TAG"; - - } - -}
--- a/vendor/sabre/vobject/lib/Property/VCard/TimeStamp.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,69 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\VCard; - -use - Sabre\VObject\DateTimeParser, - Sabre\VObject\Property\Text; - -/** - * TimeStamp property - * - * This object encodes TIMESTAMP values. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class TimeStamp extends Text { - - /** - * In case this is a multi-value property. This string will be used as a - * delimiter. - * - * @var string|null - */ - public $delimiter = null; - - /** - * Returns the type of value. - * - * This corresponds to the VALUE= parameter. Every property also has a - * 'default' valueType. - * - * @return string - */ - public function getValueType() { - - return "TIMESTAMP"; - - } - - /** - * Returns the value, in the format it should be encoded for json. - * - * This method must always return an array. - * - * @return array - */ - public function getJsonValue() { - - $parts = DateTimeParser::parseVCardDateTime($this->getValue()); - - $dateStr = - $parts['year'] . '-' . - $parts['month'] . '-' . - $parts['date'] . 'T' . - $parts['hour'] . ':' . - $parts['minute'] . ':' . - $parts['second']; - - // Timezone - if (!is_null($parts['timezone'])) { - $dateStr.=$parts['timezone']; - } - - return array($dateStr); - - } -}
--- a/vendor/sabre/vobject/lib/Reader.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,73 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * iCalendar/vCard/jCal/jCard reader object. - * - * This object provides a few (static) convenience methods to quickly access - * the parsers. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Reader { - - /** - * If this option is passed to the reader, it will be less strict about the - * validity of the lines. - */ - const OPTION_FORGIVING = 1; - - /** - * If this option is turned on, any lines we cannot parse will be ignored - * by the reader. - */ - const OPTION_IGNORE_INVALID_LINES = 2; - - /** - * Parses a vCard or iCalendar object, and returns the top component. - * - * The options argument is a bitfield. Pass any of the OPTIONS constant to - * alter the parsers' behaviour. - * - * You can either supply a string, or a readable stream for input. - * - * @param string|resource $data - * @param int $options - * @return Document - */ - static public function read($data, $options = 0) { - - $parser = new Parser\MimeDir(); - $result = $parser->parse($data, $options); - - return $result; - - } - - /** - * Parses a jCard or jCal object, and returns the top component. - * - * The options argument is a bitfield. Pass any of the OPTIONS constant to - * alter the parsers' behaviour. - * - * You can either a string, a readable stream, or an array for it's input. - * Specifying the array is useful if json_decode was already called on the - * input. - * - * @param string|resource|array $data - * @param int $options - * @return Node - */ - static public function readJson($data, $options = 0) { - - $parser = new Parser\Json(); - $result = $parser->parse($data, $options); - - return $result; - - } - -}
--- a/vendor/sabre/vobject/lib/Recur/EventIterator.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,497 +0,0 @@ -<?php - -namespace Sabre\VObject\Recur; - -use InvalidArgumentException; -use DateTime; -use DateTimeZone; -use Sabre\VObject\Component; -use Sabre\VObject\Component\VEvent; - -/** - * This class is used to determine new for a recurring event, when the next - * events occur. - * - * This iterator may loop infinitely in the future, therefore it is important - * that if you use this class, you set hard limits for the amount of iterations - * you want to handle. - * - * Note that currently there is not full support for the entire iCalendar - * specification, as it's very complex and contains a lot of permutations - * that's not yet used very often in software. - * - * For the focus has been on features as they actually appear in Calendaring - * software, but this may well get expanded as needed / on demand - * - * The following RRULE properties are supported - * * UNTIL - * * INTERVAL - * * COUNT - * * FREQ=DAILY - * * BYDAY - * * BYHOUR - * * BYMONTH - * * FREQ=WEEKLY - * * BYDAY - * * BYHOUR - * * WKST - * * FREQ=MONTHLY - * * BYMONTHDAY - * * BYDAY - * * BYSETPOS - * * FREQ=YEARLY - * * BYMONTH - * * BYMONTHDAY (only if BYMONTH is also set) - * * BYDAY (only if BYMONTH is also set) - * - * Anything beyond this is 'undefined', which means that it may get ignored, or - * you may get unexpected results. The effect is that in some applications the - * specified recurrence may look incorrect, or is missing. - * - * The recurrence iterator also does not yet support THISANDFUTURE. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class EventIterator implements \Iterator { - - /** - * Reference timeZone for floating dates and times. - * - * @var DateTimeZone - */ - protected $timeZone; - - /** - * True if we're iterating an all-day event. - * - * @var bool - */ - protected $allDay = false; - - /** - * Creates the iterator - * - * You should pass a VCALENDAR component, as well as the UID of the event - * we're going to traverse. - * - * @param Component $vcal - * @param string|null $uid - * @param DateTimeZone $timeZone Reference timezone for floating dates and - * times. - */ - public function __construct(Component $vcal, $uid = null, DateTimeZone $timeZone = null) { - - if (is_null($this->timeZone)) { - $timeZone = new DateTimeZone('UTC'); - } - $this->timeZone = $timeZone; - - if ($vcal instanceof VEvent) { - // Single instance mode. - $events = array($vcal); - } else { - $uid = (string)$uid; - if (!$uid) { - throw new InvalidArgumentException('The UID argument is required when a VCALENDAR is passed to this constructor'); - } - if (!isset($vcal->VEVENT)) { - throw new InvalidArgumentException('No events found in this calendar'); - } - $events = array(); - foreach($vcal->VEVENT as $event) { - if ($event->uid->getValue() === $uid) { - $events[] = $event; - } - } - - } - - foreach($events as $vevent) { - - if (!isset($vevent->{'RECURRENCE-ID'})) { - - $this->masterEvent = $vevent; - - } else { - - $this->exceptions[ - $vevent->{'RECURRENCE-ID'}->getDateTime($this->timeZone)->getTimeStamp() - ] = true; - $this->overriddenEvents[] = $vevent; - - } - - } - - if (!$this->masterEvent) { - // No base event was found. CalDAV does allow cases where only - // overridden instances are stored. - // - // In this particular case, we're just going to grab the first - // event and use that instead. This may not always give the - // desired result. - if (!count($this->overriddenEvents)) { - throw new InvalidArgumentException('This VCALENDAR did not have an event with UID: ' . $uid); - } - $this->masterEvent = array_shift($this->overriddenEvents); - } - - $this->startDate = $this->masterEvent->DTSTART->getDateTime($this->timeZone); - $this->allDay = !$this->masterEvent->DTSTART->hasTime(); - - if (isset($this->masterEvent->EXDATE)) { - - foreach($this->masterEvent->EXDATE as $exDate) { - - foreach($exDate->getDateTimes($this->timeZone) as $dt) { - $this->exceptions[$dt->getTimeStamp()] = true; - } - - } - - } - - if (isset($this->masterEvent->DTEND)) { - $this->eventDuration = - $this->masterEvent->DTEND->getDateTime($this->timeZone)->getTimeStamp() - - $this->startDate->getTimeStamp(); - } elseif (isset($this->masterEvent->DURATION)) { - $duration = $this->masterEvent->DURATION->getDateInterval(); - $end = clone $this->startDate; - $end->add($duration); - $this->eventDuration = $end->getTimeStamp() - $this->startDate->getTimeStamp(); - } elseif ($this->allDay) { - $this->eventDuration = 3600 * 24; - } else { - $this->eventDuration = 0; - } - - if (isset($this->masterEvent->RDATE)) { - $this->recurIterator = new RDateIterator( - $this->masterEvent->RDATE->getParts(), - $this->startDate - ); - } elseif (isset($this->masterEvent->RRULE)) { - $this->recurIterator = new RRuleIterator( - $this->masterEvent->RRULE->getParts(), - $this->startDate - ); - } else { - $this->recurIterator = new RRuleIterator( - array( - 'FREQ' => 'DAILY', - 'COUNT' => 1, - ), - $this->startDate - ); - } - - $this->rewind(); - if (!$this->valid()) { - throw new NoInstancesException('This recurrence rule does not generate any valid instances'); - } - - } - - /** - * Returns the date for the current position of the iterator. - * - * @return DateTime - */ - public function current() { - - if ($this->currentDate) { - return clone $this->currentDate; - } - - } - - /** - * This method returns the start date for the current iteration of the - * event. - * - * @return DateTime - */ - public function getDtStart() { - - if ($this->currentDate) { - return clone $this->currentDate; - } - - } - - /** - * This method returns the end date for the current iteration of the - * event. - * - * @return DateTime - */ - public function getDtEnd() { - - if (!$this->valid()) { - return null; - } - $end = clone $this->currentDate; - $end->modify('+' . $this->eventDuration . ' seconds'); - return $end; - - } - - /** - * Returns a VEVENT for the current iterations of the event. - * - * This VEVENT will have a recurrence id, and it's DTSTART and DTEND - * altered. - * - * @return VEvent - */ - public function getEventObject() { - - if ($this->currentOverriddenEvent) { - return $this->currentOverriddenEvent; - } - - $event = clone $this->masterEvent; - - // Ignoring the following block, because PHPUnit's code coverage - // ignores most of these lines, and this messes with our stats. - // - // @codeCoverageIgnoreStart - unset( - $event->RRULE, - $event->EXDATE, - $event->RDATE, - $event->EXRULE, - $event->{'RECURRENCE-ID'} - ); - // @codeCoverageIgnoreEnd - - $event->DTSTART->setDateTime($this->getDtStart()); - if (isset($event->DTEND)) { - $event->DTEND->setDateTime($this->getDtEnd()); - } - // Including a RECURRENCE-ID to the object, unless this is the first - // object. - // - // The inner recurIterator is always one step ahead, this is why we're - // checking for the key being higher than 1. - if ($this->recurIterator->key() > 1) { - $recurid = clone $event->DTSTART; - $recurid->name = 'RECURRENCE-ID'; - $event->add($recurid); - } - return $event; - - } - - /** - * Returns the current position of the iterator. - * - * This is for us simply a 0-based index. - * - * @return int - */ - public function key() { - - // The counter is always 1 ahead. - return $this->counter - 1; - - } - - /** - * This is called after next, to see if the iterator is still at a valid - * position, or if it's at the end. - * - * @return bool - */ - public function valid() { - - return !!$this->currentDate; - - } - - /** - * Sets the iterator back to the starting point. - */ - public function rewind() { - - $this->recurIterator->rewind(); - // re-creating overridden event index. - $index = array(); - foreach($this->overriddenEvents as $key=>$event) { - $stamp = $event->DTSTART->getDateTime($this->timeZone)->getTimeStamp(); - $index[$stamp] = $key; - } - krsort($index); - $this->counter = 0; - $this->overriddenEventsIndex = $index; - $this->currentOverriddenEvent = null; - - $this->nextDate = null; - $this->currentDate = clone $this->startDate; - - $this->next(); - - } - - /** - * Advances the iterator with one step. - * - * @return void - */ - public function next() { - - $this->currentOverriddenEvent = null; - $this->counter++; - if ($this->nextDate) { - // We had a stored value. - $nextDate = $this->nextDate; - $this->nextDate = null; - } else { - // We need to ask rruleparser for the next date. - // We need to do this until we find a date that's not in the - // exception list. - do { - if (!$this->recurIterator->valid()) { - $nextDate = null; - break; - } - $nextDate = $this->recurIterator->current(); - $this->recurIterator->next(); - } while(isset($this->exceptions[$nextDate->getTimeStamp()])); - - } - - - // $nextDate now contains what rrule thinks is the next one, but an - // overridden event may cut ahead. - if ($this->overriddenEventsIndex) { - - $offset = end($this->overriddenEventsIndex); - $timestamp = key($this->overriddenEventsIndex); - if (!$nextDate || $timestamp < $nextDate->getTimeStamp()) { - // Overridden event comes first. - $this->currentOverriddenEvent = $this->overriddenEvents[$offset]; - - // Putting the rrule next date aside. - $this->nextDate = $nextDate; - $this->currentDate = $this->currentOverriddenEvent->DTSTART->getDateTime($this->timeZone); - - // Ensuring that this item will only be used once. - array_pop($this->overriddenEventsIndex); - - // Exit point! - return; - - } - - } - - $this->currentDate = $nextDate; - - } - - /** - * Quickly jump to a date in the future. - * - * @param DateTime $dateTime - */ - public function fastForward(DateTime $dateTime) { - - while($this->valid() && $this->getDtEnd() < $dateTime ) { - $this->next(); - } - - } - - /** - * Returns true if this recurring event never ends. - * - * @return bool - */ - public function isInfinite() { - - return $this->recurIterator->isInfinite(); - - } - - /** - * RRULE parser - * - * @var RRuleIterator - */ - protected $recurIterator; - - /** - * The duration, in seconds, of the master event. - * - * We use this to calculate the DTEND for subsequent events. - */ - protected $eventDuration; - - /** - * A reference to the main (master) event. - * - * @var VEVENT - */ - protected $masterEvent; - - /** - * List of overridden events. - * - * @var array - */ - protected $overriddenEvents = array(); - - /** - * Overridden event index. - * - * Key is timestamp, value is the index of the item in the $overriddenEvent - * property. - * - * @var array - */ - protected $overriddenEventsIndex; - - /** - * A list of recurrence-id's that are either part of EXDATE, or are - * overridden. - * - * @var array - */ - protected $exceptions = array(); - - /** - * Internal event counter - * - * @var int - */ - protected $counter; - - /** - * The very start of the iteration process. - * - * @var DateTime - */ - protected $startDate; - - /** - * Where we are currently in the iteration process - * - * @var DateTime - */ - protected $currentDate; - - /** - * The next date from the rrule parser. - * - * Sometimes we need to temporary store the next date, because an - * overridden event came before. - * - * @var DateTime - */ - protected $nextDate; - -}
--- a/vendor/sabre/vobject/lib/Recur/NoInstancesException.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,18 +0,0 @@ -<?php - -namespace Sabre\VObject\Recur; - -use Exception; - -/** - * This exception gets thrown when a recurrence iterator produces 0 instances. - * - * This may happen when every occurence in a rrule is also in EXDATE. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://code.google.com/p/sabredav/wiki/License Modified BSD License - */ -class NoInstancesException extends Exception { - -}
--- a/vendor/sabre/vobject/lib/Recur/RDateIterator.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,174 +0,0 @@ -<?php - -namespace Sabre\VObject\Recur; - -use DateTime; -use InvalidArgumentException; -use Iterator; -use Sabre\VObject\DateTimeParser; - - -/** - * RRuleParser - * - * This class receives an RRULE string, and allows you to iterate to get a list - * of dates in that recurrence. - * - * For instance, passing: FREQ=DAILY;LIMIT=5 will cause the iterator to contain - * 5 items, one for each day. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class RDateIterator implements Iterator { - - /** - * Creates the Iterator. - * - * @param string|array $rrule - * @param DateTime $start - */ - public function __construct($rrule, DateTime $start) { - - $this->startDate = $start; - $this->parseRDate($rrule); - $this->currentDate = clone $this->startDate; - - } - - /* Implementation of the Iterator interface {{{ */ - - public function current() { - - if (!$this->valid()) return null; - return clone $this->currentDate; - - } - - /** - * Returns the current item number. - * - * @return int - */ - public function key() { - - return $this->counter; - - } - - /** - * Returns whether the current item is a valid item for the recurrence - * iterator. - * - * @return bool - */ - public function valid() { - - return ($this->counter <= count($this->dates)); - - } - - /** - * Resets the iterator. - * - * @return void - */ - public function rewind() { - - $this->currentDate = clone $this->startDate; - $this->counter = 0; - - } - - /** - * Goes on to the next iteration. - * - * @return void - */ - public function next() { - - $this->counter++; - if (!$this->valid()) return; - - $this->currentDate = - DateTimeParser::parse( - $this->dates[$this->counter-1] - ); - - } - - /* End of Iterator implementation }}} */ - - /** - * Returns true if this recurring event never ends. - * - * @return bool - */ - public function isInfinite() { - - return false; - - } - - /** - * This method allows you to quickly go to the next occurrence after the - * specified date. - * - * @param DateTime $dt - * @return void - */ - public function fastForward(\DateTime $dt) { - - while($this->valid() && $this->currentDate < $dt ) { - $this->next(); - } - - } - - /** - * The reference start date/time for the rrule. - * - * All calculations are based on this initial date. - * - * @var DateTime - */ - protected $startDate; - - /** - * The date of the current iteration. You can get this by calling - * ->current(). - * - * @var DateTime - */ - protected $currentDate; - - /** - * The current item in the list. - * - * You can get this number with the key() method. - * - * @var int - */ - protected $counter = 0; - - /* }}} */ - - /** - * This method receives a string from an RRULE property, and populates this - * class with all the values. - * - * @param string|array $rrule - * @return void - */ - protected function parseRDate($rdate) { - - if (is_string($rdate)) { - $rdate = explode(',', $rdate); - } - - $this->dates = $rdate; - - } - -}
--- a/vendor/sabre/vobject/lib/Recur/RRuleIterator.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,901 +0,0 @@ -<?php - -namespace Sabre\VObject\Recur; - -use DateTime; -use InvalidArgumentException; -use Iterator; -use Sabre\VObject\DateTimeParser; -use Sabre\VObject\Property; - - -/** - * RRuleParser - * - * This class receives an RRULE string, and allows you to iterate to get a list - * of dates in that recurrence. - * - * For instance, passing: FREQ=DAILY;LIMIT=5 will cause the iterator to contain - * 5 items, one for each day. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class RRuleIterator implements Iterator { - - /** - * Creates the Iterator - * - * @param string|array $rrule - * @param DateTime $start - */ - public function __construct($rrule, DateTime $start) { - - $this->startDate = $start; - $this->parseRRule($rrule); - $this->currentDate = clone $this->startDate; - - } - - /* Implementation of the Iterator interface {{{ */ - - public function current() { - - if (!$this->valid()) return null; - return clone $this->currentDate; - - } - - /** - * Returns the current item number - * - * @return int - */ - public function key() { - - return $this->counter; - - } - - /** - * Returns whether the current item is a valid item for the recurrence - * iterator. This will return false if we've gone beyond the UNTIL or COUNT - * statements. - * - * @return bool - */ - public function valid() { - - if (!is_null($this->count)) { - return $this->counter < $this->count; - } - return is_null($this->until) || $this->currentDate <= $this->until; - - } - - /** - * Resets the iterator - * - * @return void - */ - public function rewind() { - - $this->currentDate = clone $this->startDate; - $this->counter = 0; - - } - - /** - * Goes on to the next iteration - * - * @return void - */ - public function next() { - - $previousStamp = $this->currentDate->getTimeStamp(); - - // Otherwise, we find the next event in the normal RRULE - // sequence. - switch($this->frequency) { - - case 'hourly' : - $this->nextHourly(); - break; - - case 'daily' : - $this->nextDaily(); - break; - - case 'weekly' : - $this->nextWeekly(); - break; - - case 'monthly' : - $this->nextMonthly(); - break; - - case 'yearly' : - $this->nextYearly(); - break; - - } - $this->counter++; - - } - - /* End of Iterator implementation }}} */ - - /** - * Returns true if this recurring event never ends. - * - * @return bool - */ - public function isInfinite() { - - return !$this->count && !$this->until; - - } - - /** - * This method allows you to quickly go to the next occurrence after the - * specified date. - * - * @param DateTime $dt - * @return void - */ - public function fastForward(\DateTime $dt) { - - while($this->valid() && $this->currentDate < $dt ) { - $this->next(); - } - - } - - /** - * The reference start date/time for the rrule. - * - * All calculations are based on this initial date. - * - * @var DateTime - */ - protected $startDate; - - /** - * The date of the current iteration. You can get this by calling - * ->current(). - * - * @var DateTime - */ - protected $currentDate; - - /** - * Frequency is one of: secondly, minutely, hourly, daily, weekly, monthly, - * yearly. - * - * @var string - */ - protected $frequency; - - /** - * The number of recurrences, or 'null' if infinitely recurring. - * - * @var int - */ - protected $count; - - /** - * The interval. - * - * If for example frequency is set to daily, interval = 2 would mean every - * 2 days. - * - * @var int - */ - protected $interval = 1; - - /** - * The last instance of this recurrence, inclusively - * - * @var \DateTime|null - */ - protected $until; - - /** - * Which seconds to recur. - * - * This is an array of integers (between 0 and 60) - * - * @var array - */ - protected $bySecond; - - /** - * Which minutes to recur - * - * This is an array of integers (between 0 and 59) - * - * @var array - */ - protected $byMinute; - - /** - * Which hours to recur - * - * This is an array of integers (between 0 and 23) - * - * @var array - */ - protected $byHour; - - /** - * The current item in the list. - * - * You can get this number with the key() method. - * - * @var int - */ - protected $counter = 0; - - /** - * Which weekdays to recur. - * - * This is an array of weekdays - * - * This may also be preceeded by a positive or negative integer. If present, - * this indicates the nth occurrence of a specific day within the monthly or - * yearly rrule. For instance, -2TU indicates the second-last tuesday of - * the month, or year. - * - * @var array - */ - protected $byDay; - - /** - * Which days of the month to recur - * - * This is an array of days of the months (1-31). The value can also be - * negative. -5 for instance means the 5th last day of the month. - * - * @var array - */ - protected $byMonthDay; - - /** - * Which days of the year to recur. - * - * This is an array with days of the year (1 to 366). The values can also - * be negative. For instance, -1 will always represent the last day of the - * year. (December 31st). - * - * @var array - */ - protected $byYearDay; - - /** - * Which week numbers to recur. - * - * This is an array of integers from 1 to 53. The values can also be - * negative. -1 will always refer to the last week of the year. - * - * @var array - */ - protected $byWeekNo; - - /** - * Which months to recur. - * - * This is an array of integers from 1 to 12. - * - * @var array - */ - protected $byMonth; - - /** - * Which items in an existing st to recur. - * - * These numbers work together with an existing by* rule. It specifies - * exactly which items of the existing by-rule to filter. - * - * Valid values are 1 to 366 and -1 to -366. As an example, this can be - * used to recur the last workday of the month. - * - * This would be done by setting frequency to 'monthly', byDay to - * 'MO,TU,WE,TH,FR' and bySetPos to -1. - * - * @var array - */ - protected $bySetPos; - - /** - * When the week starts. - * - * @var string - */ - protected $weekStart = 'MO'; - - /* Functions that advance the iterator {{{ */ - - /** - * Does the processing for advancing the iterator for hourly frequency. - * - * @return void - */ - protected function nextHourly() { - - $this->currentDate->modify('+' . $this->interval . ' hours'); - - } - - /** - * Does the processing for advancing the iterator for daily frequency. - * - * @return void - */ - protected function nextDaily() { - - if (!$this->byHour && !$this->byDay) { - $this->currentDate->modify('+' . $this->interval . ' days'); - return; - } - - if (isset($this->byHour)) { - $recurrenceHours = $this->getHours(); - } - - if (isset($this->byDay)) { - $recurrenceDays = $this->getDays(); - } - - if (isset($this->byMonth)) { - $recurrenceMonths = $this->getMonths(); - } - - do { - if ($this->byHour) { - if ($this->currentDate->format('G') == '23') { - // to obey the interval rule - $this->currentDate->modify('+' . $this->interval-1 . ' days'); - } - - $this->currentDate->modify('+1 hours'); - - } else { - $this->currentDate->modify('+' . $this->interval . ' days'); - - } - - // Current month of the year - $currentMonth = $this->currentDate->format('n'); - - // Current day of the week - $currentDay = $this->currentDate->format('w'); - - // Current hour of the day - $currentHour = $this->currentDate->format('G'); - - } while ( - ($this->byDay && !in_array($currentDay, $recurrenceDays)) || - ($this->byHour && !in_array($currentHour, $recurrenceHours)) || - ($this->byMonth && !in_array($currentMonth, $recurrenceMonths)) - ); - - } - - /** - * Does the processing for advancing the iterator for weekly frequency. - * - * @return void - */ - protected function nextWeekly() { - - if (!$this->byHour && !$this->byDay) { - $this->currentDate->modify('+' . $this->interval . ' weeks'); - return; - } - - if ($this->byHour) { - $recurrenceHours = $this->getHours(); - } - - if ($this->byDay) { - $recurrenceDays = $this->getDays(); - } - - // First day of the week: - $firstDay = $this->dayMap[$this->weekStart]; - - do { - - if ($this->byHour) { - $this->currentDate->modify('+1 hours'); - } else { - $this->currentDate->modify('+1 days'); - } - - // Current day of the week - $currentDay = (int) $this->currentDate->format('w'); - - // Current hour of the day - $currentHour = (int) $this->currentDate->format('G'); - - // We need to roll over to the next week - if ($currentDay === $firstDay && (!$this->byHour || $currentHour == '0')) { - $this->currentDate->modify('+' . $this->interval-1 . ' weeks'); - - // We need to go to the first day of this week, but only if we - // are not already on this first day of this week. - if($this->currentDate->format('w') != $firstDay) { - $this->currentDate->modify('last ' . $this->dayNames[$this->dayMap[$this->weekStart]]); - } - } - - // We have a match - } while (($this->byDay && !in_array($currentDay, $recurrenceDays)) || ($this->byHour && !in_array($currentHour, $recurrenceHours))); - } - - /** - * Does the processing for advancing the iterator for monthly frequency. - * - * @return void - */ - protected function nextMonthly() { - - $currentDayOfMonth = $this->currentDate->format('j'); - if (!$this->byMonthDay && !$this->byDay) { - - // If the current day is higher than the 28th, rollover can - // occur to the next month. We Must skip these invalid - // entries. - if ($currentDayOfMonth < 29) { - $this->currentDate->modify('+' . $this->interval . ' months'); - } else { - $increase = 0; - do { - $increase++; - $tempDate = clone $this->currentDate; - $tempDate->modify('+ ' . ($this->interval*$increase) . ' months'); - } while ($tempDate->format('j') != $currentDayOfMonth); - $this->currentDate = $tempDate; - } - return; - } - - while(true) { - - $occurrences = $this->getMonthlyOccurrences(); - - foreach($occurrences as $occurrence) { - - // The first occurrence thats higher than the current - // day of the month wins. - if ($occurrence > $currentDayOfMonth) { - break 2; - } - - } - - // If we made it all the way here, it means there were no - // valid occurrences, and we need to advance to the next - // month. - // - // This line does not currently work in hhvm. Temporary workaround - // follows: - // $this->currentDate->modify('first day of this month'); - $this->currentDate = new \DateTime($this->currentDate->format('Y-m-1 H:i:s'), $this->currentDate->getTimezone()); - // end of workaround - $this->currentDate->modify('+ ' . $this->interval . ' months'); - - // This goes to 0 because we need to start counting at the - // beginning. - $currentDayOfMonth = 0; - - } - - $this->currentDate->setDate($this->currentDate->format('Y'), $this->currentDate->format('n'), $occurrence); - - } - - /** - * Does the processing for advancing the iterator for yearly frequency. - * - * @return void - */ - protected function nextYearly() { - - $currentMonth = $this->currentDate->format('n'); - $currentYear = $this->currentDate->format('Y'); - $currentDayOfMonth = $this->currentDate->format('j'); - - // No sub-rules, so we just advance by year - if (!$this->byMonth) { - - // Unless it was a leap day! - if ($currentMonth==2 && $currentDayOfMonth==29) { - - $counter = 0; - do { - $counter++; - // Here we increase the year count by the interval, until - // we hit a date that's also in a leap year. - // - // We could just find the next interval that's dividable by - // 4, but that would ignore the rule that there's no leap - // year every year that's dividable by a 100, but not by - // 400. (1800, 1900, 2100). So we just rely on the datetime - // functions instead. - $nextDate = clone $this->currentDate; - $nextDate->modify('+ ' . ($this->interval*$counter) . ' years'); - } while ($nextDate->format('n')!=2); - $this->currentDate = $nextDate; - - return; - - } - - // The easiest form - $this->currentDate->modify('+' . $this->interval . ' years'); - return; - - } - - $currentMonth = $this->currentDate->format('n'); - $currentYear = $this->currentDate->format('Y'); - $currentDayOfMonth = $this->currentDate->format('j'); - - $advancedToNewMonth = false; - - // If we got a byDay or getMonthDay filter, we must first expand - // further. - if ($this->byDay || $this->byMonthDay) { - - while(true) { - - $occurrences = $this->getMonthlyOccurrences(); - - foreach($occurrences as $occurrence) { - - // The first occurrence that's higher than the current - // day of the month wins. - // If we advanced to the next month or year, the first - // occurrence is always correct. - if ($occurrence > $currentDayOfMonth || $advancedToNewMonth) { - break 2; - } - - } - - // If we made it here, it means we need to advance to - // the next month or year. - $currentDayOfMonth = 1; - $advancedToNewMonth = true; - do { - - $currentMonth++; - if ($currentMonth>12) { - $currentYear+=$this->interval; - $currentMonth = 1; - } - } while (!in_array($currentMonth, $this->byMonth)); - - $this->currentDate->setDate($currentYear, $currentMonth, $currentDayOfMonth); - - } - - // If we made it here, it means we got a valid occurrence - $this->currentDate->setDate($currentYear, $currentMonth, $occurrence); - return; - - } else { - - // These are the 'byMonth' rules, if there are no byDay or - // byMonthDay sub-rules. - do { - - $currentMonth++; - if ($currentMonth>12) { - $currentYear+=$this->interval; - $currentMonth = 1; - } - } while (!in_array($currentMonth, $this->byMonth)); - $this->currentDate->setDate($currentYear, $currentMonth, $currentDayOfMonth); - - return; - - } - - } - - /* }}} */ - - /** - * This method receives a string from an RRULE property, and populates this - * class with all the values. - * - * @param string|array $rrule - * @return void - */ - protected function parseRRule($rrule) { - - if (is_string($rrule)) { - $rrule = Property\ICalendar\Recur::stringToArray($rrule); - } - - foreach($rrule as $key=>$value) { - - $key = strtoupper($key); - switch($key) { - - case 'FREQ' : - $value = strtolower($value); - if (!in_array( - $value, - array('secondly','minutely','hourly','daily','weekly','monthly','yearly') - )) { - throw new InvalidArgumentException('Unknown value for FREQ=' . strtoupper($value)); - } - $this->frequency = $value; - break; - - case 'UNTIL' : - $this->until = DateTimeParser::parse($value, $this->startDate->getTimezone()); - - // In some cases events are generated with an UNTIL= - // parameter before the actual start of the event. - // - // Not sure why this is happening. We assume that the - // intention was that the event only recurs once. - // - // So we are modifying the parameter so our code doesn't - // break. - if($this->until < $this->startDate) { - $this->until = $this->startDate; - } - break; - - case 'INTERVAL' : - // No break - - case 'COUNT' : - $val = (int)$value; - if ($val < 1) { - throw new \InvalidArgumentException(strtoupper($key) . ' in RRULE must be a positive integer!'); - } - $key = strtolower($key); - $this->$key = $val; - break; - - case 'BYSECOND' : - $this->bySecond = (array)$value; - break; - - case 'BYMINUTE' : - $this->byMinute = (array)$value; - break; - - case 'BYHOUR' : - $this->byHour = (array)$value; - break; - - case 'BYDAY' : - $value = (array)$value; - foreach($value as $part) { - if (!preg_match('#^ (-|\+)? ([1-5])? (MO|TU|WE|TH|FR|SA|SU) $# xi', $part)) { - throw new \InvalidArgumentException('Invalid part in BYDAY clause: ' . $part); - } - } - $this->byDay = $value; - break; - - case 'BYMONTHDAY' : - $this->byMonthDay = (array)$value; - break; - - case 'BYYEARDAY' : - $this->byYearDay = (array)$value; - break; - - case 'BYWEEKNO' : - $this->byWeekNo = (array)$value; - break; - - case 'BYMONTH' : - $this->byMonth = (array)$value; - break; - - case 'BYSETPOS' : - $this->bySetPos = (array)$value; - break; - - case 'WKST' : - $this->weekStart = strtoupper($value); - break; - - default: - throw new \InvalidArgumentException('Not supported: ' . strtoupper($key)); - - } - - } - - } - - /** - * Mappings between the day number and english day name. - * - * @var array - */ - protected $dayNames = array( - 0 => 'Sunday', - 1 => 'Monday', - 2 => 'Tuesday', - 3 => 'Wednesday', - 4 => 'Thursday', - 5 => 'Friday', - 6 => 'Saturday', - ); - - /** - * Returns all the occurrences for a monthly frequency with a 'byDay' or - * 'byMonthDay' expansion for the current month. - * - * The returned list is an array of integers with the day of month (1-31). - * - * @return array - */ - protected function getMonthlyOccurrences() { - - $startDate = clone $this->currentDate; - - $byDayResults = array(); - - // Our strategy is to simply go through the byDays, advance the date to - // that point and add it to the results. - if ($this->byDay) foreach($this->byDay as $day) { - - $dayName = $this->dayNames[$this->dayMap[substr($day,-2)]]; - - - // Dayname will be something like 'wednesday'. Now we need to find - // all wednesdays in this month. - $dayHits = array(); - - // workaround for missing 'first day of the month' support in hhvm - $checkDate = new \DateTime($startDate->format('Y-m-1')); - // workaround modify always advancing the date even if the current day is a $dayName in hhvm - if ($checkDate->format('l') !== $dayName) { - $checkDate->modify($dayName); - } - - do { - $dayHits[] = $checkDate->format('j'); - $checkDate->modify('next ' . $dayName); - } while ($checkDate->format('n') === $startDate->format('n')); - - // So now we have 'all wednesdays' for month. It is however - // possible that the user only really wanted the 1st, 2nd or last - // wednesday. - if (strlen($day)>2) { - $offset = (int)substr($day,0,-2); - - if ($offset>0) { - // It is possible that the day does not exist, such as a - // 5th or 6th wednesday of the month. - if (isset($dayHits[$offset-1])) { - $byDayResults[] = $dayHits[$offset-1]; - } - } else { - - // if it was negative we count from the end of the array - $byDayResults[] = $dayHits[count($dayHits) + $offset]; - } - } else { - // There was no counter (first, second, last wednesdays), so we - // just need to add the all to the list). - $byDayResults = array_merge($byDayResults, $dayHits); - - } - - } - - $byMonthDayResults = array(); - if ($this->byMonthDay) foreach($this->byMonthDay as $monthDay) { - - // Removing values that are out of range for this month - if ($monthDay > $startDate->format('t') || - $monthDay < 0-$startDate->format('t')) { - continue; - } - if ($monthDay>0) { - $byMonthDayResults[] = $monthDay; - } else { - // Negative values - $byMonthDayResults[] = $startDate->format('t') + 1 + $monthDay; - } - } - - // If there was just byDay or just byMonthDay, they just specify our - // (almost) final list. If both were provided, then byDay limits the - // list. - if ($this->byMonthDay && $this->byDay) { - $result = array_intersect($byMonthDayResults, $byDayResults); - } elseif ($this->byMonthDay) { - $result = $byMonthDayResults; - } else { - $result = $byDayResults; - } - $result = array_unique($result); - sort($result, SORT_NUMERIC); - - // The last thing that needs checking is the BYSETPOS. If it's set, it - // means only certain items in the set survive the filter. - if (!$this->bySetPos) { - return $result; - } - - $filteredResult = array(); - foreach($this->bySetPos as $setPos) { - - if ($setPos<0) { - $setPos = count($result)-($setPos+1); - } - if (isset($result[$setPos-1])) { - $filteredResult[] = $result[$setPos-1]; - } - } - - sort($filteredResult, SORT_NUMERIC); - return $filteredResult; - - } - - /** - * Simple mapping from iCalendar day names to day numbers - * - * @var array - */ - protected $dayMap = array( - 'SU' => 0, - 'MO' => 1, - 'TU' => 2, - 'WE' => 3, - 'TH' => 4, - 'FR' => 5, - 'SA' => 6, - ); - - protected function getHours() - { - $recurrenceHours = array(); - foreach($this->byHour as $byHour) { - $recurrenceHours[] = $byHour; - } - - return $recurrenceHours; - } - - protected function getDays() { - - $recurrenceDays = array(); - foreach($this->byDay as $byDay) { - - // The day may be preceeded with a positive (+n) or - // negative (-n) integer. However, this does not make - // sense in 'weekly' so we ignore it here. - $recurrenceDays[] = $this->dayMap[substr($byDay,-2)]; - - } - - return $recurrenceDays; - } - - protected function getMonths() { - - $recurrenceMonths = array(); - foreach($this->byMonth as $byMonth) { - $recurrenceMonths[] = $byMonth; - } - - return $recurrenceMonths; - } -}
--- a/vendor/sabre/vobject/lib/RecurrenceIterator.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,21 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use Sabre\VObject\Recur\EventIterator; - -/** - * RecurrenceIterator - * - * This class is deprecated. Use Sabre\VObject\Recur\EventIterator instead. - * This class will be removed from a future version. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @deprecated - * @license http://sabre.io/license Modified BSD License - */ -class RecurrenceIterator extends EventIterator { - - -}
--- a/vendor/sabre/vobject/lib/Splitter/ICalendar.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,116 +0,0 @@ -<?php - -namespace Sabre\VObject\Splitter; - -use - Sabre\VObject, - Sabre\VObject\Component\VCalendar; - -/** - * Splitter - * - * This class is responsible for splitting up iCalendar objects. - * - * This class expects a single VCALENDAR object with one or more - * calendar-objects inside. Objects with identical UID's will be combined into - * a single object. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Dominik Tobschall - * @author Armin Hackmann - * @license http://sabre.io/license/ Modified BSD License - */ -class ICalendar implements SplitterInterface { - - /** - * Timezones - * - * @var array - */ - protected $vtimezones = array(); - - /** - * iCalendar objects - * - * @var array - */ - protected $objects = array(); - - /** - * Constructor - * - * The splitter should receive an readable file stream as it's input. - * - * @param resource $input - * @param int $options Parser options, see the OPTIONS constants. - */ - public function __construct($input, $options = 0) { - - $data = VObject\Reader::read($input, $options); - $vtimezones = array(); - $components = array(); - - if (!$data instanceof VObject\Component\VCalendar) { - throw new VObject\ParseException('Supplied input could not be parsed as VCALENDAR.'); - } - - foreach($data->children() as $component) { - if (!$component instanceof VObject\Component) { - continue; - } - - // Get all timezones - if ($component->name === 'VTIMEZONE') { - $this->vtimezones[(string)$component->TZID] = $component; - continue; - } - - // Get component UID for recurring Events search - if(!$component->UID) { - $component->UID = sha1(microtime()) . '-vobjectimport'; - } - $uid = (string)$component->UID; - - // Take care of recurring events - if (!array_key_exists($uid, $this->objects)) { - $this->objects[$uid] = new VCalendar(); - } - - $this->objects[$uid]->add(clone $component); - } - - } - - /** - * Every time getNext() is called, a new object will be parsed, until we - * hit the end of the stream. - * - * When the end is reached, null will be returned. - * - * @return Sabre\VObject\Component|null - */ - public function getNext() { - - if($object=array_shift($this->objects)) { - - // create our baseobject - $object->version = '2.0'; - $object->prodid = '-//Sabre//Sabre VObject ' . VObject\Version::VERSION . '//EN'; - $object->calscale = 'GREGORIAN'; - - // add vtimezone information to obj (if we have it) - foreach ($this->vtimezones as $vtimezone) { - $object->add($vtimezone); - } - - return $object; - - } else { - - return null; - - } - - } - -}
--- a/vendor/sabre/vobject/lib/Splitter/SplitterInterface.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,39 +0,0 @@ -<?php - -namespace Sabre\VObject\Splitter; - -/** - * VObject splitter - * - * The splitter is responsible for reading a large vCard or iCalendar object, - * and splitting it into multiple objects. - * - * This is for example for Card and CalDAV, which require every event and vcard - * to exist in their own objects, instead of one large one. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Dominik Tobschall - * @license http://sabre.io/license/ Modified BSD License - */ -interface SplitterInterface { - - /** - * Constructor - * - * The splitter should receive an readable file stream as it's input. - * - * @param resource $input - */ - public function __construct($input); - - /** - * Every time getNext() is called, a new object will be parsed, until we - * hit the end of the stream. - * - * When the end is reached, null will be returned. - * - * @return Sabre\VObject\Component|null - */ - public function getNext(); - -}
--- a/vendor/sabre/vobject/lib/Splitter/VCard.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,79 +0,0 @@ -<?php - -namespace Sabre\VObject\Splitter; - -use - Sabre\VObject, - Sabre\VObject\Parser\MimeDir; - -/** - * Splitter - * - * This class is responsible for splitting up VCard objects. - * - * It is assumed that the input stream contains 1 or more VCARD objects. This - * class checks for BEGIN:VCARD and END:VCARD and parses each encountered - * component individually. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Dominik Tobschall - * @author Armin Hackmann - * @license http://sabre.io/license/ Modified BSD License - */ -class VCard implements SplitterInterface { - - /** - * File handle - * - * @var resource - */ - protected $input; - - /** - * Persistent parser - * - * @var MimeDir - */ - protected $parser; - - /** - * Constructor - * - * The splitter should receive an readable file stream as it's input. - * - * @param resource $input - * @param int $options Parser options, see the OPTIONS constants. - */ - public function __construct($input, $options = 0) { - - $this->input = $input; - $this->parser = new MimeDir($input, $options); - - } - - /** - * Every time getNext() is called, a new object will be parsed, until we - * hit the end of the stream. - * - * When the end is reached, null will be returned. - * - * @return Sabre\VObject\Component|null - */ - public function getNext() { - - try { - $object = $this->parser->parse(); - - if (!$object instanceof VObject\Component\VCard) { - throw new VObject\ParseException('The supplied input contained non-VCARD data.'); - } - - } catch (VObject\EofException $e) { - return null; - } - - return $object; - - } - -}
--- a/vendor/sabre/vobject/lib/StringUtil.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,65 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Useful utilities for working with various strings. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class StringUtil { - - /** - * Returns true or false depending on if a string is valid UTF-8 - * - * @param string $str - * @return bool - */ - static public function isUTF8($str) { - - // Control characters - if (preg_match('%[\x00-\x08\x0B-\x0C\x0E\x0F]%', $str)) { - return false; - } - - return (bool)preg_match('%%u', $str); - - } - - /** - * This method tries its best to convert the input string to UTF-8. - * - * Currently only ISO-5991-1 input and UTF-8 input is supported, but this - * may be expanded upon if we receive other examples. - * - * @param string $str - * @return string - */ - static public function convertToUTF8($str) { - - $encoding = mb_detect_encoding($str , array('UTF-8','ISO-8859-1', 'WINDOWS-1252'), true); - - switch($encoding) { - case 'ISO-8859-1' : - $newStr = utf8_encode($str); - break; - /* Unreachable code. Not sure yet how we can improve this - * situation. - case 'WINDOWS-1252' : - $newStr = iconv('cp1252', 'UTF-8', $str); - break; - */ - default : - $newStr = $str; - - } - - // Removing any control characters - return (preg_replace('%(?:[\x00-\x08\x0B-\x0C\x0E-\x1F\x7F])%', '', $newStr)); - - } - -} -
--- a/vendor/sabre/vobject/lib/TimeZoneUtil.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,265 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Time zone name translation - * - * This file translates well-known time zone names into "Olson database" time zone names. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Frank Edelhaeuser (fedel@users.sourceforge.net) - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class TimeZoneUtil { - - public static $map = null; - - /** - * List of microsoft exchange timezone ids. - * - * Source: http://msdn.microsoft.com/en-us/library/aa563018(loband).aspx - */ - public static $microsoftExchangeMap = array( - 0 => 'UTC', - 31 => 'Africa/Casablanca', - - // Insanely, id #2 is used for both Europe/Lisbon, and Europe/Sarajevo. - // I'm not even kidding.. We handle this special case in the - // getTimeZone method. - 2 => 'Europe/Lisbon', - 1 => 'Europe/London', - 4 => 'Europe/Berlin', - 6 => 'Europe/Prague', - 3 => 'Europe/Paris', - 69 => 'Africa/Luanda', // This was a best guess - 7 => 'Europe/Athens', - 5 => 'Europe/Bucharest', - 49 => 'Africa/Cairo', - 50 => 'Africa/Harare', - 59 => 'Europe/Helsinki', - 27 => 'Asia/Jerusalem', - 26 => 'Asia/Baghdad', - 74 => 'Asia/Kuwait', - 51 => 'Europe/Moscow', - 56 => 'Africa/Nairobi', - 25 => 'Asia/Tehran', - 24 => 'Asia/Muscat', // Best guess - 54 => 'Asia/Baku', - 48 => 'Asia/Kabul', - 58 => 'Asia/Yekaterinburg', - 47 => 'Asia/Karachi', - 23 => 'Asia/Calcutta', - 62 => 'Asia/Kathmandu', - 46 => 'Asia/Almaty', - 71 => 'Asia/Dhaka', - 66 => 'Asia/Colombo', - 61 => 'Asia/Rangoon', - 22 => 'Asia/Bangkok', - 64 => 'Asia/Krasnoyarsk', - 45 => 'Asia/Shanghai', - 63 => 'Asia/Irkutsk', - 21 => 'Asia/Singapore', - 73 => 'Australia/Perth', - 75 => 'Asia/Taipei', - 20 => 'Asia/Tokyo', - 72 => 'Asia/Seoul', - 70 => 'Asia/Yakutsk', - 19 => 'Australia/Adelaide', - 44 => 'Australia/Darwin', - 18 => 'Australia/Brisbane', - 76 => 'Australia/Sydney', - 43 => 'Pacific/Guam', - 42 => 'Australia/Hobart', - 68 => 'Asia/Vladivostok', - 41 => 'Asia/Magadan', - 17 => 'Pacific/Auckland', - 40 => 'Pacific/Fiji', - 67 => 'Pacific/Tongatapu', - 29 => 'Atlantic/Azores', - 53 => 'Atlantic/Cape_Verde', - 30 => 'America/Noronha', - 8 => 'America/Sao_Paulo', // Best guess - 32 => 'America/Argentina/Buenos_Aires', - 60 => 'America/Godthab', - 28 => 'America/St_Johns', - 9 => 'America/Halifax', - 33 => 'America/Caracas', - 65 => 'America/Santiago', - 35 => 'America/Bogota', - 10 => 'America/New_York', - 34 => 'America/Indiana/Indianapolis', - 55 => 'America/Guatemala', - 11 => 'America/Chicago', - 37 => 'America/Mexico_City', - 36 => 'America/Edmonton', - 38 => 'America/Phoenix', - 12 => 'America/Denver', // Best guess - 13 => 'America/Los_Angeles', // Best guess - 14 => 'America/Anchorage', - 15 => 'Pacific/Honolulu', - 16 => 'Pacific/Midway', - 39 => 'Pacific/Kwajalein', - ); - - /** - * This method will try to find out the correct timezone for an iCalendar - * date-time value. - * - * You must pass the contents of the TZID parameter, as well as the full - * calendar. - * - * If the lookup fails, this method will return the default PHP timezone - * (as configured using date_default_timezone_set, or the date.timezone ini - * setting). - * - * Alternatively, if $failIfUncertain is set to true, it will throw an - * exception if we cannot accurately determine the timezone. - * - * @param string $tzid - * @param Sabre\VObject\Component $vcalendar - * @return DateTimeZone - */ - static public function getTimeZone($tzid, Component $vcalendar = null, $failIfUncertain = false) { - - // First we will just see if the tzid is a support timezone identifier. - // - // The only exception is if the timezone starts with (. This is to - // handle cases where certain microsoft products generate timezone - // identifiers that for instance look like: - // - // (GMT+01.00) Sarajevo/Warsaw/Zagreb - // - // Since PHP 5.5.10, the first bit will be used as the timezone and - // this method will return just GMT+01:00. This is wrong, because it - // doesn't take DST into account. - if ($tzid[0]!=='(') { - - // PHP has a bug that logs PHP warnings even it shouldn't: - // https://bugs.php.net/bug.php?id=67881 - // - // That's why we're checking if we'll be able to successfull instantiate - // \DateTimeZone() before doing so. Otherwise we could simply instantiate - // and catch the exception. - $tzIdentifiers = \DateTimeZone::listIdentifiers(); - - try { - if ( - (in_array($tzid, $tzIdentifiers)) || - (preg_match('/^GMT(\+|-)([0-9]{4})$/', $tzid, $matches)) || - (in_array($tzid, self::getIdentifiersBC())) - ) { - return new \DateTimeZone($tzid); - } - } catch(\Exception $e) { - } - - } - - self::loadTzMaps(); - - // Next, we check if the tzid is somewhere in our tzid map. - if (isset(self::$map[$tzid])) { - return new \DateTimeZone(self::$map[$tzid]); - } - - // Maybe the author was hyper-lazy and just included an offset. We - // support it, but we aren't happy about it. - if (preg_match('/^GMT(\+|-)([0-9]{4})$/', $tzid, $matches)) { - - // Note that the path in the source will never be taken from PHP 5.5.10 - // onwards. PHP 5.5.10 supports the "GMT+0100" style of format, so it - // already gets returned early in this function. Once we drop support - // for versions under PHP 5.5.10, this bit can be taken out of the - // source. - // @codeCoverageIgnoreStart - return new \DateTimeZone('Etc/GMT' . $matches[1] . ltrim(substr($matches[2],0,2),'0')); - // @codeCoverageIgnoreEnd - } - - if ($vcalendar) { - - // If that didn't work, we will scan VTIMEZONE objects - foreach($vcalendar->select('VTIMEZONE') as $vtimezone) { - - if ((string)$vtimezone->TZID === $tzid) { - - // Some clients add 'X-LIC-LOCATION' with the olson name. - if (isset($vtimezone->{'X-LIC-LOCATION'})) { - - $lic = (string)$vtimezone->{'X-LIC-LOCATION'}; - - // Libical generators may specify strings like - // "SystemV/EST5EDT". For those we must remove the - // SystemV part. - if (substr($lic,0,8)==='SystemV/') { - $lic = substr($lic,8); - } - - return self::getTimeZone($lic, null, $failIfUncertain); - - } - // Microsoft may add a magic number, which we also have an - // answer for. - if (isset($vtimezone->{'X-MICROSOFT-CDO-TZID'})) { - $cdoId = (int)$vtimezone->{'X-MICROSOFT-CDO-TZID'}->getValue(); - - // 2 can mean both Europe/Lisbon and Europe/Sarajevo. - if ($cdoId===2 && strpos((string)$vtimezone->TZID, 'Sarajevo')!==false) { - return new \DateTimeZone('Europe/Sarajevo'); - } - - if (isset(self::$microsoftExchangeMap[$cdoId])) { - return new \DateTimeZone(self::$microsoftExchangeMap[$cdoId]); - } - } - - } - - } - - } - - if ($failIfUncertain) { - throw new \InvalidArgumentException('We were unable to determine the correct PHP timezone for tzid: ' . $tzid); - } - - // If we got all the way here, we default to UTC. - return new \DateTimeZone(date_default_timezone_get()); - - } - - /** - * This method will load in all the tz mapping information, if it's not yet - * done. - */ - static public function loadTzMaps() { - - if (!is_null(self::$map)) return; - - self::$map = array_merge( - include __DIR__ . '/timezonedata/windowszones.php', - include __DIR__ . '/timezonedata/lotuszones.php', - include __DIR__ . '/timezonedata/exchangezones.php', - include __DIR__ . '/timezonedata/php-workaround.php' - ); - - } - - /** - * This method returns an array of timezone identifiers, that are supported - * by DateTimeZone(), but not returned by DateTimeZone::listIdentifiers() - * - * We're not using DateTimeZone::listIdentifiers(DateTimeZone::ALL_WITH_BC) because: - * - It's not supported by some PHP versions as well as HHVM. - * - It also returns identifiers, that are invalid values for new DateTimeZone() on some PHP versions. - * (See timezonedata/php-bc.php and timezonedata php-workaround.php) - * - * @return array - */ - static public function getIdentifiersBC() { - return include __DIR__ . '/timezonedata/php-bc.php'; - } - -}
--- a/vendor/sabre/vobject/lib/UUIDUtil.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,67 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * UUID Utility - * - * This class has static methods to generate and validate UUID's. - * UUIDs are used a decent amount within various *DAV standards, so it made - * sense to include it. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class UUIDUtil { - - /** - * Returns a pseudo-random v4 UUID - * - * This function is based on a comment by Andrew Moore on php.net - * - * @see http://www.php.net/manual/en/function.uniqid.php#94959 - * @return string - */ - static public function getUUID() { - - return sprintf( - - '%04x%04x-%04x-%04x-%04x-%04x%04x%04x', - - // 32 bits for "time_low" - mt_rand( 0, 0xffff ), mt_rand( 0, 0xffff ), - - // 16 bits for "time_mid" - mt_rand( 0, 0xffff ), - - // 16 bits for "time_hi_and_version", - // four most significant bits holds version number 4 - mt_rand( 0, 0x0fff ) | 0x4000, - - // 16 bits, 8 bits for "clk_seq_hi_res", - // 8 bits for "clk_seq_low", - // two most significant bits holds zero and one for variant DCE1.1 - mt_rand( 0, 0x3fff ) | 0x8000, - - // 48 bits for "node" - mt_rand( 0, 0xffff ), mt_rand( 0, 0xffff ), mt_rand( 0, 0xffff ) - ); - } - - /** - * Checks if a string is a valid UUID. - * - * @param string $uuid - * @return bool - */ - static public function validateUUID($uuid) { - - return preg_match( - '/^[a-f0-9]{8}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{4}-[a-f0-9]{12}$/i', - $uuid - ) == true; - - } - -}
--- a/vendor/sabre/vobject/lib/VCardConverter.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,459 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * This utility converts vcards from one version to another. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class VCardConverter { - - /** - * Converts a vCard object to a new version. - * - * targetVersion must be one of: - * Document::VCARD21 - * Document::VCARD30 - * Document::VCARD40 - * - * Currently only 3.0 and 4.0 as input and output versions. - * - * 2.1 has some minor support for the input version, it's incomplete at the - * moment though. - * - * If input and output version are identical, a clone is returned. - * - * @param Component\VCard $input - * @param int $targetVersion - */ - public function convert(Component\VCard $input, $targetVersion) { - - $inputVersion = $input->getDocumentType(); - if ($inputVersion===$targetVersion) { - return clone $input; - } - - if (!in_array($inputVersion, array(Document::VCARD21, Document::VCARD30, Document::VCARD40))) { - throw new \InvalidArgumentException('Only vCard 2.1, 3.0 and 4.0 are supported for the input data'); - } - if (!in_array($targetVersion, array(Document::VCARD30, Document::VCARD40))) { - throw new \InvalidArgumentException('You can only use vCard 3.0 or 4.0 for the target version'); - } - - $newVersion = $targetVersion===Document::VCARD40?'4.0':'3.0'; - - $output = new Component\VCard(array( - 'VERSION' => $newVersion, - )); - - foreach($input->children as $property) { - - $this->convertProperty($input, $output, $property, $targetVersion); - - } - - return $output; - - } - - /** - * Handles conversion of a single property. - * - * @param Component\VCard $input - * @param Component\VCard $output - * @param Property $property - * @param int $targetVersion - * @return void - */ - protected function convertProperty(Component\VCard $input, Component\VCard $output, Property $property, $targetVersion) { - - // Skipping these, those are automatically added. - if (in_array($property->name, array('VERSION', 'PRODID'))) { - return; - } - - $parameters = $property->parameters(); - $valueType = null; - if (isset($parameters['VALUE'])) { - $valueType = $parameters['VALUE']->getValue(); - unset($parameters['VALUE']); - } - if (!$valueType) { - $valueType = $property->getValueType(); - } - $newProperty = $output->createProperty( - $property->name, - $property->getParts(), - array(), // parameters will get added a bit later. - $valueType - ); - - - if ($targetVersion===Document::VCARD30) { - - if ($property instanceof Property\Uri && in_array($property->name, array('PHOTO','LOGO','SOUND'))) { - - $newProperty = $this->convertUriToBinary($output, $newProperty); - - } elseif ($property instanceof Property\VCard\DateAndOrTime) { - - // In vCard 4, the birth year may be optional. This is not the - // case for vCard 3. Apple has a workaround for this that - // allows applications that support Apple's extension still - // omit birthyears in vCard 3, but applications that do not - // support this, will just use a random birthyear. We're - // choosing 1604 for the birthyear, because that's what apple - // uses. - $parts = DateTimeParser::parseVCardDateTime($property->getValue()); - if (is_null($parts['year'])) { - $newValue = '1604-' . $parts['month'] . '-' . $parts['date']; - $newProperty->setValue($newValue); - $newProperty['X-APPLE-OMIT-YEAR'] = '1604'; - } - - if ($newProperty->name == 'ANNIVERSARY') { - // Microsoft non-standard anniversary - $newProperty->name = 'X-ANNIVERSARY'; - - // We also need to add a new apple property for the same - // purpose. This apple property needs a 'label' in the same - // group, so we first need to find a groupname that doesn't - // exist yet. - $x = 1; - while($output->select('ITEM' . $x . '.')) { - $x++; - } - $output->add('ITEM' . $x . '.X-ABDATE', $newProperty->getValue(), array('VALUE' => 'DATE-AND-OR-TIME')); - $output->add('ITEM' . $x . '.X-ABLABEL', '_$!<Anniversary>!$_'); - } - - } elseif ($property->name === 'KIND') { - - switch(strtolower($property->getValue())) { - case 'org' : - // vCard 3.0 does not have an equivalent to KIND:ORG, - // but apple has an extension that means the same - // thing. - $newProperty = $output->createProperty('X-ABSHOWAS','COMPANY'); - break; - - case 'individual' : - // Individual is implicit, so we skip it. - return; - - case 'group' : - // OS X addressbook property - $newProperty = $output->createProperty('X-ADDRESSBOOKSERVER-KIND','GROUP'); - break; - } - - - } - - } elseif ($targetVersion===Document::VCARD40) { - - // These properties were removed in vCard 4.0 - if (in_array($property->name, array('NAME', 'MAILER', 'LABEL', 'CLASS'))) { - return; - } - - if ($property instanceof Property\Binary) { - - $newProperty = $this->convertBinaryToUri($output, $newProperty, $parameters); - - } elseif ($property instanceof Property\VCard\DateAndOrTime && isset($parameters['X-APPLE-OMIT-YEAR'])) { - - // If a property such as BDAY contained 'X-APPLE-OMIT-YEAR', - // then we're stripping the year from the vcard 4 value. - $parts = DateTimeParser::parseVCardDateTime($property->getValue()); - if ($parts['year']===$property['X-APPLE-OMIT-YEAR']->getValue()) { - $newValue = '--' . $parts['month'] . '-' . $parts['date']; - $newProperty->setValue($newValue); - } - - // Regardless if the year matched or not, we do need to strip - // X-APPLE-OMIT-YEAR. - unset($parameters['X-APPLE-OMIT-YEAR']); - - } - switch($property->name) { - case 'X-ABSHOWAS' : - if (strtoupper($property->getValue()) === 'COMPANY') { - $newProperty = $output->createProperty('KIND','ORG'); - } - break; - case 'X-ADDRESSBOOKSERVER-KIND' : - if (strtoupper($property->getValue()) === 'GROUP') { - $newProperty = $output->createProperty('KIND','GROUP'); - } - break; - case 'X-ANNIVERSARY' : - $newProperty->name = 'ANNIVERSARY'; - // If we already have an anniversary property with the same - // value, ignore. - foreach ($output->select('ANNIVERSARY') as $anniversary) { - if ($anniversary->getValue() === $newProperty->getValue()) { - return; - } - } - break; - case 'X-ABDATE' : - // Find out what the label was, if it exists. - if (!$property->group) { - break; - } - $label = $input->{$property->group . '.X-ABLABEL'}; - - // We only support converting anniversaries. - if (!$label || $label->getValue()!=='_$!<Anniversary>!$_') { - break; - } - - // If we already have an anniversary property with the same - // value, ignore. - foreach ($output->select('ANNIVERSARY') as $anniversary) { - if ($anniversary->getValue() === $newProperty->getValue()) { - return; - } - } - $newProperty->name = 'ANNIVERSARY'; - break; - // Apple's per-property label system. - case 'X-ABLABEL' : - if($newProperty->getValue() === '_$!<Anniversary>!$_') { - // We can safely remove these, as they are converted to - // ANNIVERSARY properties. - return; - } - break; - - } - - } - - // set property group - $newProperty->group = $property->group; - - if ($targetVersion===Document::VCARD40) { - $this->convertParameters40($newProperty, $parameters); - } else { - $this->convertParameters30($newProperty, $parameters); - } - - // Lastly, we need to see if there's a need for a VALUE parameter. - // - // We can do that by instantating a empty property with that name, and - // seeing if the default valueType is identical to the current one. - $tempProperty = $output->createProperty($newProperty->name); - if ($tempProperty->getValueType() !== $newProperty->getValueType()) { - $newProperty['VALUE'] = $newProperty->getValueType(); - } - - $output->add($newProperty); - - - } - - /** - * Converts a BINARY property to a URI property. - * - * vCard 4.0 no longer supports BINARY properties. - * - * @param Component\VCard $output - * @param Property\Uri $property The input property. - * @param $parameters List of parameters that will eventually be added to - * the new property. - * @return Property\Uri - */ - protected function convertBinaryToUri(Component\VCard $output, Property\Binary $newProperty, array &$parameters) { - - $value = $newProperty->getValue(); - $newProperty = $output->createProperty( - $newProperty->name, - null, // no value - array(), // no parameters yet - 'URI' // Forcing the BINARY type - ); - - $mimeType = 'application/octet-stream'; - - // See if we can find a better mimetype. - if (isset($parameters['TYPE'])) { - - $newTypes = array(); - foreach($parameters['TYPE']->getParts() as $typePart) { - if (in_array( - strtoupper($typePart), - array('JPEG','PNG','GIF') - )) { - $mimeType = 'image/' . strtolower($typePart); - } else { - $newTypes[] = $typePart; - } - } - - // If there were any parameters we're not converting to a - // mime-type, we need to keep them. - if ($newTypes) { - $parameters['TYPE']->setParts($newTypes); - } else { - unset($parameters['TYPE']); - } - - } - - $newProperty->setValue('data:' . $mimeType . ';base64,' . base64_encode($value)); - return $newProperty; - - } - - /** - * Converts a URI property to a BINARY property. - * - * In vCard 4.0 attachments are encoded as data: uri. Even though these may - * be valid in vCard 3.0 as well, we should convert those to BINARY if - * possible, to improve compatibility. - * - * @param Component\VCard $output - * @param Property\Uri $property The input property. - * @return Property\Binary|null - */ - protected function convertUriToBinary(Component\VCard $output, Property\Uri $newProperty) { - - $value = $newProperty->getValue(); - - // Only converting data: uris - if (substr($value, 0, 5)!=='data:') { - return $newProperty; - } - - $newProperty = $output->createProperty( - $newProperty->name, - null, // no value - array(), // no parameters yet - 'BINARY' - ); - - $mimeType = substr($value, 5, strpos($value, ',')-5); - if (strpos($mimeType, ';')) { - $mimeType = substr($mimeType,0,strpos($mimeType, ';')); - $newProperty->setValue(base64_decode(substr($value, strpos($value,',')+1))); - } else { - $newProperty->setValue(substr($value, strpos($value,',')+1)); - } - unset($value); - - $newProperty['ENCODING'] = 'b'; - switch($mimeType) { - - case 'image/jpeg' : - $newProperty['TYPE'] = 'JPEG'; - break; - case 'image/png' : - $newProperty['TYPE'] = 'PNG'; - break; - case 'image/gif' : - $newProperty['TYPE'] = 'GIF'; - break; - - } - - - return $newProperty; - - } - - /** - * Adds parameters to a new property for vCard 4.0 - * - * @param Property $newProperty - * @param array $parameters - * @return void - */ - protected function convertParameters40(Property $newProperty, array $parameters) { - - // Adding all parameters. - foreach($parameters as $param) { - - // vCard 2.1 allowed parameters with no name - if ($param->noName) $param->noName = false; - - switch($param->name) { - - // We need to see if there's any TYPE=PREF, because in vCard 4 - // that's now PREF=1. - case 'TYPE' : - foreach($param->getParts() as $paramPart) { - - if (strtoupper($paramPart)==='PREF') { - $newProperty->add('PREF','1'); - } else { - $newProperty->add($param->name, $paramPart); - } - - } - break; - // These no longer exist in vCard 4 - case 'ENCODING' : - case 'CHARSET' : - break; - - default : - $newProperty->add($param->name, $param->getParts()); - break; - - } - - } - - } - - /** - * Adds parameters to a new property for vCard 3.0 - * - * @param Property $newProperty - * @param array $parameters - * @return void - */ - protected function convertParameters30(Property $newProperty, array $parameters) { - - // Adding all parameters. - foreach($parameters as $param) { - - // vCard 2.1 allowed parameters with no name - if ($param->noName) $param->noName = false; - - switch($param->name) { - - case 'ENCODING' : - // This value only existed in vCard 2.1, and should be - // removed for anything else. - if (strtoupper($param->getValue())!=='QUOTED-PRINTABLE') { - $newProperty->add($param->name, $param->getParts()); - } - break; - - /* - * Converting PREF=1 to TYPE=PREF. - * - * Any other PREF numbers we'll drop. - */ - case 'PREF' : - if ($param->getValue()=='1') { - $newProperty->add('TYPE','PREF'); - } - break; - - default : - $newProperty->add($param->name, $param->getParts()); - break; - - } - - } - - } -}
--- a/vendor/sabre/vobject/lib/Version.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,19 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * This class contains the version number for the VObject package - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -class Version { - - /** - * Full version number - */ - const VERSION = '3.3.5'; - -}
--- a/vendor/sabre/vobject/lib/timezonedata/exchangezones.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,93 +0,0 @@ -<?php - -/** - * Microsoft exchange timezones - * Source: - * http://msdn.microsoft.com/en-us/library/ms988620%28v=exchg.65%29.aspx - * - * Correct timezones deduced with help from: - * http://en.wikipedia.org/wiki/List_of_tz_database_time_zones - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @license http://sabre.io/license/ Modified BSD License - */ -return array( - 'Universal Coordinated Time' => 'UTC', - 'Casablanca, Monrovia' => 'Africa/Casablanca', - 'Greenwich Mean Time: Dublin, Edinburgh, Lisbon, London' => 'Europe/Lisbon', - 'Greenwich Mean Time; Dublin, Edinburgh, London' => 'Europe/London', - 'Amsterdam, Berlin, Bern, Rome, Stockholm, Vienna' => 'Europe/Berlin', - 'Belgrade, Pozsony, Budapest, Ljubljana, Prague' => 'Europe/Prague', - 'Brussels, Copenhagen, Madrid, Paris' => 'Europe/Paris', - 'Paris, Madrid, Brussels, Copenhagen' => 'Europe/Paris', - 'Prague, Central Europe' => 'Europe/Prague', - 'Sarajevo, Skopje, Sofija, Vilnius, Warsaw, Zagreb' => 'Europe/Sarajevo', - 'West Central Africa' => 'Africa/Luanda', // This was a best guess - 'Athens, Istanbul, Minsk' => 'Europe/Athens', - 'Bucharest' => 'Europe/Bucharest', - 'Cairo' => 'Africa/Cairo', - 'Harare, Pretoria' => 'Africa/Harare', - 'Helsinki, Riga, Tallinn' => 'Europe/Helsinki', - 'Israel, Jerusalem Standard Time' => 'Asia/Jerusalem', - 'Baghdad' => 'Asia/Baghdad', - 'Arab, Kuwait, Riyadh' => 'Asia/Kuwait', - 'Moscow, St. Petersburg, Volgograd' => 'Europe/Moscow', - 'East Africa, Nairobi' => 'Africa/Nairobi', - 'Tehran' => 'Asia/Tehran', - 'Abu Dhabi, Muscat' => 'Asia/Muscat', // Best guess - 'Baku, Tbilisi, Yerevan' => 'Asia/Baku', - 'Kabul' => 'Asia/Kabul', - 'Ekaterinburg' => 'Asia/Yekaterinburg', - 'Islamabad, Karachi, Tashkent' => 'Asia/Karachi', - 'Kolkata, Chennai, Mumbai, New Delhi, India Standard Time' => 'Asia/Calcutta', - 'Kathmandu, Nepal' => 'Asia/Kathmandu', - 'Almaty, Novosibirsk, North Central Asia' => 'Asia/Almaty', - 'Astana, Dhaka' => 'Asia/Dhaka', - 'Sri Jayawardenepura, Sri Lanka' => 'Asia/Colombo', - 'Rangoon' => 'Asia/Rangoon', - 'Bangkok, Hanoi, Jakarta' => 'Asia/Bangkok', - 'Krasnoyarsk' => 'Asia/Krasnoyarsk', - 'Beijing, Chongqing, Hong Kong SAR, Urumqi' => 'Asia/Shanghai', - 'Irkutsk, Ulaan Bataar' => 'Asia/Irkutsk', - 'Kuala Lumpur, Singapore' => 'Asia/Singapore', - 'Perth, Western Australia' => 'Australia/Perth', - 'Taipei' => 'Asia/Taipei', - 'Osaka, Sapporo, Tokyo' => 'Asia/Tokyo', - 'Seoul, Korea Standard time' => 'Asia/Seoul', - 'Yakutsk' => 'Asia/Yakutsk', - 'Adelaide, Central Australia' => 'Australia/Adelaide', - 'Darwin' => 'Australia/Darwin', - 'Brisbane, East Australia' => 'Australia/Brisbane', - 'Canberra, Melbourne, Sydney, Hobart (year 2000 only)' => 'Australia/Sydney', - 'Guam, Port Moresby' => 'Pacific/Guam', - 'Hobart, Tasmania' => 'Australia/Hobart', - 'Vladivostok' => 'Asia/Vladivostok', - 'Magadan, Solomon Is., New Caledonia' => 'Asia/Magadan', - 'Auckland, Wellington' => 'Pacific/Auckland', - 'Fiji Islands, Kamchatka, Marshall Is.' => 'Pacific/Fiji', - 'Nuku\'alofa, Tonga' => 'Pacific/Tongatapu', - 'Azores' => 'Atlantic/Azores', - 'Cape Verde Is.' => 'Atlantic/Cape_Verde', - 'Mid-Atlantic' => 'America/Noronha', - 'Brasilia' => 'America/Sao_Paulo', // Best guess - 'Buenos Aires' => 'America/Argentina/Buenos_Aires', - 'Greenland' => 'America/Godthab', - 'Newfoundland' => 'America/St_Johns', - 'Atlantic Time (Canada)' => 'America/Halifax', - 'Caracas, La Paz' => 'America/Caracas', - 'Santiago' => 'America/Santiago', - 'Bogota, Lima, Quito' => 'America/Bogota', - 'Eastern Time (US & Canada)' => 'America/New_York', - 'Indiana (East)' => 'America/Indiana/Indianapolis', - 'Central America' => 'America/Guatemala', - 'Central Time (US & Canada)' => 'America/Chicago', - 'Mexico City, Tegucigalpa' => 'America/Mexico_City', - 'Saskatchewan' => 'America/Edmonton', - 'Arizona' => 'America/Phoenix', - 'Mountain Time (US & Canada)' => 'America/Denver', // Best guess - 'Pacific Time (US & Canada); Tijuana' => 'America/Los_Angeles', // Best guess - 'Alaska' => 'America/Anchorage', - 'Hawaii' => 'Pacific/Honolulu', - 'Midway Island, Samoa' => 'Pacific/Midway', - 'Eniwetok, Kwajalein, Dateline Time' => 'Pacific/Kwajalein', -);
--- a/vendor/sabre/vobject/lib/timezonedata/lotuszones.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,101 +0,0 @@ -<?php - -/** - * The following list are timezone names that could be generated by - * Lotus / Domino - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @license http://sabre.io/license/ Modified BSD License - */ -return array( - 'Dateline' => 'Etc/GMT-12', - 'Samoa' => 'Pacific/Apia', - 'Hawaiian' => 'Pacific/Honolulu', - 'Alaskan' => 'America/Anchorage', - 'Pacific' => 'America/Los_Angeles', - 'Pacific Standard Time' => 'America/Los_Angeles', - 'Mexico Standard Time 2' => 'America/Chihuahua', - 'Mountain' => 'America/Denver', - // 'Mountain Standard Time' => 'America/Chihuahua', // conflict with windows timezones. - 'US Mountain' => 'America/Phoenix', - 'Canada Central' => 'America/Edmonton', - 'Central America' => 'America/Guatemala', - 'Central' => 'America/Chicago', - // 'Central Standard Time' => 'America/Mexico_City', // conflict with windows timezones. - 'Mexico' => 'America/Mexico_City', - 'Eastern' => 'America/New_York', - 'SA Pacific' => 'America/Bogota', - 'US Eastern' => 'America/Indiana/Indianapolis', - 'Venezuela' => 'America/Caracas', - 'Atlantic' => 'America/Halifax', - 'Central Brazilian' => 'America/Manaus', - 'Pacific SA' => 'America/Santiago', - 'SA Western' => 'America/La_Paz', - 'Newfoundland' => 'America/St_Johns', - 'Argentina' => 'America/Argentina/Buenos_Aires', - 'E. South America' => 'America/Belem', - 'Greenland' => 'America/Godthab', - 'Montevideo' => 'America/Montevideo', - 'SA Eastern' => 'America/Belem', - // 'Mid-Atlantic' => 'Etc/GMT-2', // conflict with windows timezones. - 'Azores' => 'Atlantic/Azores', - 'Cape Verde' => 'Atlantic/Cape_Verde', - 'Greenwich' => 'Atlantic/Reykjavik', // No I'm serious.. Greenwich is not GMT. - 'Morocco' => 'Africa/Casablanca', - 'Central Europe' => 'Europe/Prague', - 'Central European' => 'Europe/Sarajevo', - 'Romance' => 'Europe/Paris', - 'W. Central Africa' => 'Africa/Lagos', // Best guess - 'W. Europe' => 'Europe/Amsterdam', - 'E. Europe' => 'Europe/Minsk', - 'Egypt' => 'Africa/Cairo', - 'FLE' => 'Europe/Helsinki', - 'GTB' => 'Europe/Athens', - 'Israel' => 'Asia/Jerusalem', - 'Jordan' => 'Asia/Amman', - 'Middle East' => 'Asia/Beirut', - 'Namibia' => 'Africa/Windhoek', - 'South Africa' => 'Africa/Harare', - 'Arab' => 'Asia/Kuwait', - 'Arabic' => 'Asia/Baghdad', - 'E. Africa' => 'Africa/Nairobi', - 'Georgian' => 'Asia/Tbilisi', - 'Russian' => 'Europe/Moscow', - 'Iran' => 'Asia/Tehran', - 'Arabian' => 'Asia/Muscat', - 'Armenian' => 'Asia/Yerevan', - 'Azerbijan' => 'Asia/Baku', - 'Caucasus' => 'Asia/Yerevan', - 'Mauritius' => 'Indian/Mauritius', - 'Afghanistan' => 'Asia/Kabul', - 'Ekaterinburg' => 'Asia/Yekaterinburg', - 'Pakistan' => 'Asia/Karachi', - 'West Asia' => 'Asia/Tashkent', - 'India' => 'Asia/Calcutta', - 'Sri Lanka' => 'Asia/Colombo', - 'Nepal' => 'Asia/Kathmandu', - 'Central Asia' => 'Asia/Dhaka', - 'N. Central Asia' => 'Asia/Almaty', - 'Myanmar' => 'Asia/Rangoon', - 'North Asia' => 'Asia/Krasnoyarsk', - 'SE Asia' => 'Asia/Bangkok', - 'China' => 'Asia/Shanghai', - 'North Asia East' => 'Asia/Irkutsk', - 'Singapore' => 'Asia/Singapore', - 'Taipei' => 'Asia/Taipei', - 'W. Australia' => 'Australia/Perth', - 'Korea' => 'Asia/Seoul', - 'Tokyo' => 'Asia/Tokyo', - 'Yakutsk' => 'Asia/Yakutsk', - 'AUS Central' => 'Australia/Darwin', - 'Cen. Australia' => 'Australia/Adelaide', - 'AUS Eastern' => 'Australia/Sydney', - 'E. Australia' => 'Australia/Brisbane', - 'Tasmania' => 'Australia/Hobart', - 'Vladivostok' => 'Asia/Vladivostok', - 'West Pacific' => 'Pacific/Guam', - 'Central Pacific' => 'Asia/Magadan', - 'Fiji' => 'Pacific/Fiji', - 'New Zealand' => 'Pacific/Auckland', - 'Tonga' => 'Pacific/Tongatapu', -);
--- a/vendor/sabre/vobject/lib/timezonedata/php-bc.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,153 +0,0 @@ -<?php -/** - * A list of additional PHP timezones that are returned by - * DateTimeZone::listIdentifiers(DateTimeZone::ALL_WITH_BC) - * valid for new DateTimeZone() - * - * This list does not include those timezone identifiers that we have to map to - * a different identifier for some PHP versions (see php-workaround.php). - * - * Instead of using DateTimeZone::listIdentifiers(DateTimeZone::ALL_WITH_BC) - * directly, we use this file because DateTimeZone::ALL_WITH_BC is not properly - * supported by all PHP version and HHVM. - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @license http://sabre.io/license/ Modified BSD License - */ -return array( - 'Africa/Asmera', - 'Africa/Timbuktu', - 'America/Argentina/ComodRivadavia', - 'America/Atka', - 'America/Buenos_Aires', - 'America/Catamarca', - 'America/Coral_Harbour', - 'America/Cordoba', - 'America/Ensenada', - 'America/Fort_Wayne', - 'America/Indianapolis', - 'America/Jujuy', - 'America/Knox_IN', - 'America/Louisville', - 'America/Mendoza', - 'America/Montreal', - 'America/Porto_Acre', - 'America/Rosario', - 'America/Shiprock', - 'America/Virgin', - 'Antarctica/South_Pole', - 'Asia/Ashkhabad', - 'Asia/Calcutta', - 'Asia/Chungking', - 'Asia/Dacca', - 'Asia/Istanbul', - 'Asia/Katmandu', - 'Asia/Macao', - 'Asia/Saigon', - 'Asia/Tel_Aviv', - 'Asia/Thimbu', - 'Asia/Ujung_Pandang', - 'Asia/Ulan_Bator', - 'Atlantic/Faeroe', - 'Atlantic/Jan_Mayen', - 'Australia/ACT', - 'Australia/Canberra', - 'Australia/LHI', - 'Australia/North', - 'Australia/NSW', - 'Australia/Queensland', - 'Australia/South', - 'Australia/Tasmania', - 'Australia/Victoria', - 'Australia/West', - 'Australia/Yancowinna', - 'Brazil/Acre', - 'Brazil/DeNoronha', - 'Brazil/East', - 'Brazil/West', - 'Canada/Atlantic', - 'Canada/Central', - 'Canada/East-Saskatchewan', - 'Canada/Eastern', - 'Canada/Mountain', - 'Canada/Newfoundland', - 'Canada/Pacific', - 'Canada/Saskatchewan', - 'Canada/Yukon', - 'CET', - 'Chile/Continental', - 'Chile/EasterIsland', - 'EET', - 'EST', - 'Etc/GMT', - 'Etc/GMT+0', - 'Etc/GMT+1', - 'Etc/GMT+10', - 'Etc/GMT+11', - 'Etc/GMT+12', - 'Etc/GMT+2', - 'Etc/GMT+3', - 'Etc/GMT+4', - 'Etc/GMT+5', - 'Etc/GMT+6', - 'Etc/GMT+7', - 'Etc/GMT+8', - 'Etc/GMT+9', - 'Etc/GMT-0', - 'Etc/GMT-1', - 'Etc/GMT-10', - 'Etc/GMT-11', - 'Etc/GMT-12', - 'Etc/GMT-13', - 'Etc/GMT-14', - 'Etc/GMT-2', - 'Etc/GMT-3', - 'Etc/GMT-4', - 'Etc/GMT-5', - 'Etc/GMT-6', - 'Etc/GMT-7', - 'Etc/GMT-8', - 'Etc/GMT-9', - 'Etc/GMT0', - 'Etc/Greenwich', - 'Etc/UCT', - 'Etc/Universal', - 'Etc/UTC', - 'Etc/Zulu', - 'Europe/Belfast', - 'Europe/Nicosia', - 'Europe/Tiraspol', - 'GB', - 'GMT', - 'GMT+0', - 'GMT-0', - 'HST', - 'MET', - 'Mexico/BajaNorte', - 'Mexico/BajaSur', - 'Mexico/General', - 'MST', - 'NZ', - 'Pacific/Ponape', - 'Pacific/Samoa', - 'Pacific/Truk', - 'Pacific/Yap', - 'PRC', - 'ROC', - 'ROK', - 'UCT', - 'US/Alaska', - 'US/Aleutian', - 'US/Arizona', - 'US/Central', - 'US/East-Indiana', - 'US/Eastern', - 'US/Hawaii', - 'US/Indiana-Starke', - 'US/Michigan', - 'US/Mountain', - 'US/Pacific', - 'US/Pacific-New', - 'US/Samoa', - 'WET', -);
--- a/vendor/sabre/vobject/lib/timezonedata/php-workaround.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,45 +0,0 @@ -<?php -/** - * A list of PHP timezones that were supported until 5.5.9, removed in - * PHP 5.5.10 and re-introduced in PHP 5.5.17 - * - * DateTimeZone::listIdentifiers(DateTimeZone::ALL_WITH_BC) returns them, - * but they are invalid for new DateTimeZone(). Fixed in PHP 5.5.17. - * https://bugs.php.net/bug.php?id=66985 - * - * Some more info here: - * http://evertpot.com/php-5-5-10-timezone-changes/ - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @license http://sabre.io/license/ Modified BSD License - */ -return array( - 'CST6CDT' => 'America/Chicago', - 'Cuba' => 'America/Havana', - 'Egypt' => 'Africa/Cairo', - 'Eire' => 'Europe/Dublin', - 'EST5EDT' => 'America/New_York', - 'Factory' => 'UTC', - 'GB-Eire' => 'Europe/London', - 'GMT0' => 'UTC', - 'Greenwich' => 'UTC', - 'Hongkong' => 'Asia/Hong_Kong', - 'Iceland' => 'Atlantic/Reykjavik', - 'Iran' => 'Asia/Tehran', - 'Israel' => 'Asia/Jerusalem', - 'Jamaica' => 'America/Jamaica', - 'Japan' => 'Asia/Tokyo', - 'Kwajalein' => 'Pacific/Kwajalein', - 'Libya' => 'Africa/Tripoli', - 'MST7MDT' => 'America/Denver', - 'Navajo' => 'America/Denver', - 'NZ-CHAT' => 'Pacific/Chatham', - 'Poland' => 'Europe/Warsaw', - 'Portugal' => 'Europe/Lisbon', - 'PST8PDT' => 'America/Los_Angeles', - 'Singapore' => 'Asia/Singapore', - 'Turkey' => 'Europe/Istanbul', - 'Universal' => 'UTC', - 'W-SU' => 'Europe/Moscow', - 'Zulu' => 'UTC', -);
--- a/vendor/sabre/vobject/lib/timezonedata/windowszones.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,114 +0,0 @@ -<?php - -/** - * Automatically generated timezone file - * - * Last update: 2014-10-03T07:58:31-04:00 - * Source: http://unicode.org/repos/cldr/trunk/common/supplemental/windowsZones.xml - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @license http://sabre.io/license/ Modified BSD License - */ - -return array ( - 'AUS Central Standard Time' => 'Australia/Darwin', - 'AUS Eastern Standard Time' => 'Australia/Sydney', - 'Afghanistan Standard Time' => 'Asia/Kabul', - 'Alaskan Standard Time' => 'America/Anchorage', - 'Arab Standard Time' => 'Asia/Riyadh', - 'Arabian Standard Time' => 'Asia/Dubai', - 'Arabic Standard Time' => 'Asia/Baghdad', - 'Argentina Standard Time' => 'America/Buenos_Aires', - 'Atlantic Standard Time' => 'America/Halifax', - 'Azerbaijan Standard Time' => 'Asia/Baku', - 'Azores Standard Time' => 'Atlantic/Azores', - 'Bahia Standard Time' => 'America/Bahia', - 'Bangladesh Standard Time' => 'Asia/Dhaka', - 'Canada Central Standard Time' => 'America/Regina', - 'Cape Verde Standard Time' => 'Atlantic/Cape_Verde', - 'Caucasus Standard Time' => 'Asia/Yerevan', - 'Cen. Australia Standard Time' => 'Australia/Adelaide', - 'Central America Standard Time' => 'America/Guatemala', - 'Central Asia Standard Time' => 'Asia/Almaty', - 'Central Brazilian Standard Time' => 'America/Cuiaba', - 'Central Europe Standard Time' => 'Europe/Budapest', - 'Central European Standard Time' => 'Europe/Warsaw', - 'Central Pacific Standard Time' => 'Pacific/Guadalcanal', - 'Central Standard Time' => 'America/Chicago', - 'Central Standard Time (Mexico)' => 'America/Mexico_City', - 'China Standard Time' => 'Asia/Shanghai', - 'Dateline Standard Time' => 'Etc/GMT+12', - 'E. Africa Standard Time' => 'Africa/Nairobi', - 'E. Australia Standard Time' => 'Australia/Brisbane', - 'E. South America Standard Time' => 'America/Sao_Paulo', - 'Eastern Standard Time' => 'America/New_York', - 'Egypt Standard Time' => 'Africa/Cairo', - 'Ekaterinburg Standard Time' => 'Asia/Yekaterinburg', - 'FLE Standard Time' => 'Europe/Kiev', - 'Fiji Standard Time' => 'Pacific/Fiji', - 'GMT Standard Time' => 'Europe/London', - 'GTB Standard Time' => 'Europe/Bucharest', - 'Georgian Standard Time' => 'Asia/Tbilisi', - 'Greenland Standard Time' => 'America/Godthab', - 'Greenwich Standard Time' => 'Atlantic/Reykjavik', - 'Hawaiian Standard Time' => 'Pacific/Honolulu', - 'India Standard Time' => 'Asia/Calcutta', - 'Iran Standard Time' => 'Asia/Tehran', - 'Israel Standard Time' => 'Asia/Jerusalem', - 'Jordan Standard Time' => 'Asia/Amman', - 'Kaliningrad Standard Time' => 'Europe/Kaliningrad', - 'Korea Standard Time' => 'Asia/Seoul', - 'Libya Standard Time' => 'Africa/Tripoli', - 'Line Islands Standard Time' => 'Pacific/Kiritimati', - 'Magadan Standard Time' => 'Asia/Magadan', - 'Mauritius Standard Time' => 'Indian/Mauritius', - 'Middle East Standard Time' => 'Asia/Beirut', - 'Montevideo Standard Time' => 'America/Montevideo', - 'Morocco Standard Time' => 'Africa/Casablanca', - 'Mountain Standard Time' => 'America/Denver', - 'Mountain Standard Time (Mexico)' => 'America/Chihuahua', - 'Myanmar Standard Time' => 'Asia/Rangoon', - 'N. Central Asia Standard Time' => 'Asia/Novosibirsk', - 'Namibia Standard Time' => 'Africa/Windhoek', - 'Nepal Standard Time' => 'Asia/Katmandu', - 'New Zealand Standard Time' => 'Pacific/Auckland', - 'Newfoundland Standard Time' => 'America/St_Johns', - 'North Asia East Standard Time' => 'Asia/Irkutsk', - 'North Asia Standard Time' => 'Asia/Krasnoyarsk', - 'Pacific SA Standard Time' => 'America/Santiago', - 'Pacific Standard Time' => 'America/Los_Angeles', - 'Pacific Standard Time (Mexico)' => 'America/Santa_Isabel', - 'Pakistan Standard Time' => 'Asia/Karachi', - 'Paraguay Standard Time' => 'America/Asuncion', - 'Romance Standard Time' => 'Europe/Paris', - 'Russian Standard Time' => 'Europe/Moscow', - 'SA Eastern Standard Time' => 'America/Cayenne', - 'SA Pacific Standard Time' => 'America/Bogota', - 'SA Western Standard Time' => 'America/La_Paz', - 'SE Asia Standard Time' => 'Asia/Bangkok', - 'Samoa Standard Time' => 'Pacific/Apia', - 'Singapore Standard Time' => 'Asia/Singapore', - 'South Africa Standard Time' => 'Africa/Johannesburg', - 'Sri Lanka Standard Time' => 'Asia/Colombo', - 'Syria Standard Time' => 'Asia/Damascus', - 'Taipei Standard Time' => 'Asia/Taipei', - 'Tasmania Standard Time' => 'Australia/Hobart', - 'Tokyo Standard Time' => 'Asia/Tokyo', - 'Tonga Standard Time' => 'Pacific/Tongatapu', - 'Turkey Standard Time' => 'Europe/Istanbul', - 'US Eastern Standard Time' => 'America/Indianapolis', - 'US Mountain Standard Time' => 'America/Phoenix', - 'UTC' => 'Etc/GMT', - 'UTC+12' => 'Etc/GMT-12', - 'UTC-02' => 'Etc/GMT+2', - 'UTC-11' => 'Etc/GMT+11', - 'Ulaanbaatar Standard Time' => 'Asia/Ulaanbaatar', - 'Venezuela Standard Time' => 'America/Caracas', - 'Vladivostok Standard Time' => 'Asia/Vladivostok', - 'W. Australia Standard Time' => 'Australia/Perth', - 'W. Central Africa Standard Time' => 'Africa/Lagos', - 'W. Europe Standard Time' => 'Europe/Berlin', - 'West Asia Standard Time' => 'Asia/Tashkent', - 'West Pacific Standard Time' => 'Pacific/Port_Moresby', - 'Yakutsk Standard Time' => 'Asia/Yakutsk', -);
--- a/vendor/sabre/vobject/tests/VObject/AttachIssueTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,22 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class AttachIssueTest extends \PHPUnit_Framework_TestCase { - - function testRead() { - - $event = <<<ICS -BEGIN:VCALENDAR\r -BEGIN:VEVENT\r -ATTACH;FMTTYPE=;ENCODING=:Zm9v\r -END:VEVENT\r -END:VCALENDAR\r - -ICS; - $obj = Reader::read($event); - $this->assertEquals($event, $obj->serialize()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/CliTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,650 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Tests the cli. - * - * Warning: these tests are very rudimentary. - */ -class CliTest extends \PHPUnit_Framework_TestCase { - - public function setUp() { - - $this->cli = new CliMock(); - $this->cli->stderr = fopen('php://memory','r+'); - $this->cli->stdout = fopen('php://memory','r+'); - - } - - public function testInvalidArg() { - - $this->assertEquals( - 1, - $this->cli->main(array('vobject', '--hi')) - ); - rewind($this->cli->stderr); - $this->assertTrue(strlen(stream_get_contents($this->cli->stderr)) > 100); - - } - - public function testQuiet() { - - $this->assertEquals( - 1, - $this->cli->main(array('vobject', '-q')) - ); - $this->assertTrue($this->cli->quiet); - - rewind($this->cli->stderr); - $this->assertEquals(0, strlen(stream_get_contents($this->cli->stderr))); - - } - - public function testHelp() { - - $this->assertEquals( - 0, - $this->cli->main(array('vobject', '-h')) - ); - rewind($this->cli->stderr); - $this->assertTrue(strlen(stream_get_contents($this->cli->stderr)) > 100); - - } - - public function testFormat() { - - $this->assertEquals( - 1, - $this->cli->main(array('vobject', '--format=jcard')) - ); - - rewind($this->cli->stderr); - $this->assertTrue(strlen(stream_get_contents($this->cli->stderr)) > 100); - - $this->assertEquals('jcard', $this->cli->format); - - } - - public function testFormatInvalid() { - - $this->assertEquals( - 1, - $this->cli->main(array('vobject', '--format=foo')) - ); - - rewind($this->cli->stderr); - $this->assertTrue(strlen(stream_get_contents($this->cli->stderr)) > 100); - - $this->assertNull($this->cli->format); - - } - - public function testInputFormatInvalid() { - - $this->assertEquals( - 1, - $this->cli->main(array('vobject', '--inputformat=foo')) - ); - - rewind($this->cli->stderr); - $this->assertTrue(strlen(stream_get_contents($this->cli->stderr)) > 100); - - $this->assertNull($this->cli->format); - - } - - - public function testNoInputFile() { - - $this->assertEquals( - 1, - $this->cli->main(array('vobject', 'color')) - ); - - rewind($this->cli->stderr); - $this->assertTrue(strlen(stream_get_contents($this->cli->stderr)) > 100); - - } - - public function testTooManyArgs() { - - $this->assertEquals( - 1, - $this->cli->main(array('vobject', 'color', 'a', 'b', 'c')) - ); - - } - - public function testUnknownCommand() { - - $this->assertEquals( - 1, - $this->cli->main(array('vobject', 'foo', '-')) - ); - - } - - public function testConvertJson() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<ICS -BEGIN:VCARD -VERSION:3.0 -FN:Cowboy Henk -END:VCARD -ICS - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - - $this->assertEquals( - 0, - $this->cli->main(array('vobject', 'convert','--format=json', '-')) - ); - - rewind($this->cli->stdout); - $version = Version::VERSION; - $this->assertEquals( - '["vcard",[["version",{},"text","4.0"],["prodid",{},"text","-\/\/Sabre\/\/Sabre VObject '. $version .'\/\/EN"],["fn",{},"text","Cowboy Henk"]]]', - stream_get_contents($this->cli->stdout) - ); - - } - - public function testConvertJCardPretty() { - - if (version_compare(PHP_VERSION, '5.4.0') < 0) { - $this->markTestSkipped('This test required PHP 5.4.0'); - } - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<ICS -BEGIN:VCARD -VERSION:3.0 -FN:Cowboy Henk -END:VCARD -ICS - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - - $this->assertEquals( - 0, - $this->cli->main(array('vobject', 'convert','--format=jcard', '--pretty', '-')) - ); - - rewind($this->cli->stdout); - $version = Version::VERSION; - - // PHP 5.5.12 changed the output - - $expected = <<<JCARD -[ - "vcard", - [ - [ - "versi -JCARD; - - $this->assertStringStartsWith( - $expected, - stream_get_contents($this->cli->stdout) - ); - - } - - public function testConvertJCalFail() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<ICS -BEGIN:VCARD -VERSION:3.0 -FN:Cowboy Henk -END:VCARD -ICS - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - - $this->assertEquals( - 2, - $this->cli->main(array('vobject', 'convert','--format=jcal', '--inputformat=mimedir', '-')) - ); - - } - - public function testConvertMimeDir() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<JCARD -[ - "vcard", - [ - [ - "version", - { - - }, - "text", - "4.0" - ], - [ - "prodid", - { - - }, - "text", - "-\/\/Sabre\/\/Sabre VObject 3.1.0\/\/EN" - ], - [ - "fn", - { - - }, - "text", - "Cowboy Henk" - ] - ] -] -JCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - - $this->assertEquals( - 0, - $this->cli->main(array('vobject', 'convert','--format=mimedir', '--inputformat=json', '--pretty', '-')) - ); - - rewind($this->cli->stdout); - $expected = <<<VCF -BEGIN:VCARD -VERSION:4.0 -PRODID:-//Sabre//Sabre VObject 3.1.0//EN -FN:Cowboy Henk -END:VCARD - -VCF; - - $this->assertEquals( - strtr($expected, array("\n"=>"\r\n")), - stream_get_contents($this->cli->stdout) - ); - - } - - public function testConvertDefaultFormats() { - - $inputStream = fopen('php://memory','r+'); - $outputFile = SABRE_TEMPDIR . 'bar.json'; - - $this->assertEquals( - 2, - $this->cli->main(array('vobject', 'convert','foo.json',$outputFile)) - ); - - $this->assertEquals('json', $this->cli->inputFormat); - $this->assertEquals('json', $this->cli->format); - - } - - public function testConvertDefaultFormats2() { - - $outputFile = SABRE_TEMPDIR . 'bar.ics'; - - $this->assertEquals( - 2, - $this->cli->main(array('vobject', 'convert','foo.ics',$outputFile)) - ); - - $this->assertEquals('mimedir', $this->cli->inputFormat); - $this->assertEquals('mimedir', $this->cli->format); - - } - - public function testVCard3040() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<VCARD -BEGIN:VCARD -VERSION:3.0 -PRODID:-//Sabre//Sabre VObject 3.1.0//EN -FN:Cowboy Henk -END:VCARD - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - - $this->assertEquals( - 0, - $this->cli->main(array('vobject', 'convert','--format=vcard40', '--pretty', '-')) - ); - - rewind($this->cli->stdout); - - $version = Version::VERSION; - $expected = <<<VCF -BEGIN:VCARD -VERSION:4.0 -PRODID:-//Sabre//Sabre VObject $version//EN -FN:Cowboy Henk -END:VCARD - -VCF; - - $this->assertEquals( - strtr($expected, array("\n"=>"\r\n")), - stream_get_contents($this->cli->stdout) - ); - - } - - public function testVCard4030() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<VCARD -BEGIN:VCARD -VERSION:4.0 -PRODID:-//Sabre//Sabre VObject 3.1.0//EN -FN:Cowboy Henk -END:VCARD - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - - $this->assertEquals( - 0, - $this->cli->main(array('vobject', 'convert','--format=vcard30', '--pretty', '-')) - ); - - $version = Version::VERSION; - - rewind($this->cli->stdout); - $expected = <<<VCF -BEGIN:VCARD -VERSION:3.0 -PRODID:-//Sabre//Sabre VObject $version//EN -FN:Cowboy Henk -END:VCARD - -VCF; - - $this->assertEquals( - strtr($expected, array("\n"=>"\r\n")), - stream_get_contents($this->cli->stdout) - ); - - } - - public function testVCard4021() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<VCARD -BEGIN:VCARD -VERSION:4.0 -PRODID:-//Sabre//Sabre VObject 3.1.0//EN -FN:Cowboy Henk -END:VCARD - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - - // vCard 2.1 is not supported yet, so this returns a failure. - $this->assertEquals( - 2, - $this->cli->main(array('vobject', 'convert','--format=vcard21', '--pretty', '-')) - ); - - } - - function testValidate() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<VCARD -BEGIN:VCARD -VERSION:4.0 -PRODID:-//Sabre//Sabre VObject 3.1.0//EN -UID:foo -FN:Cowboy Henk -END:VCARD - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - $result = $this->cli->main(array('vobject', 'validate', '-')); - - $this->assertEquals( - 0, - $result - ); - - } - - function testValidateFail() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<VCARD -BEGIN:VCALENDAR -VERSION:2.0 -END:VCARD - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - // vCard 2.1 is not supported yet, so this returns a failure. - $this->assertEquals( - 2, - $this->cli->main(array('vobject', 'validate', '-')) - ); - - } - - function testValidateFail2() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<VCARD -BEGIN:VCALENDAR -VERSION:5.0 -END:VCALENDAR - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - // vCard 2.1 is not supported yet, so this returns a failure. - $this->assertEquals( - 2, - $this->cli->main(array('vobject', 'validate', '-')) - ); - - } - - function testRepair() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<VCARD -BEGIN:VCARD -VERSION:5.0 -END:VCARD - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - // vCard 2.1 is not supported yet, so this returns a failure. - $this->assertEquals( - 2, - $this->cli->main(array('vobject', 'repair', '-')) - ); - - rewind($this->cli->stdout); - $this->assertRegExp("/^BEGIN:VCARD\r\nVERSION:2.1\r\nUID:[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}\r\nEND:VCARD\r\n$/", stream_get_contents($this->cli->stdout)); - } - - function testRepairNothing() { - - $inputStream = fopen('php://memory','r+'); - - fwrite($inputStream, <<<VCARD -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject 3.1.0//EN -BEGIN:VEVENT -UID:foo -DTSTAMP:20140122T233226Z -DTSTART:20140101T120000Z -END:VEVENT -END:VCALENDAR - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - // vCard 2.1 is not supported yet, so this returns a failure. - - $result = $this->cli->main(array('vobject', 'repair', '-')); - - rewind($this->cli->stderr); - $error = stream_get_contents($this->cli->stderr); - - $this->assertEquals( - 0, - $result, - "This should have been error free. stderr output:\n" . $error - ); - - } - - /** - * Note: this is a very shallow test, doesn't dig into the actual output, - * but just makes sure there's no errors thrown. - * - * The colorizer is not a critical component, it's mostly a debugging tool. - */ - function testColorCalendar() { - - $inputStream = fopen('php://memory','r+'); - - $version = Version::VERSION; - - /** - * This object is not valid, but it's designed to hit every part of the - * colorizer source. - */ - fwrite($inputStream, <<<VCARD -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject {$version}//EN -BEGIN:VTIMEZONE -END:VTIMEZONE -BEGIN:VEVENT -ATTENDEE;RSVP=TRUE:mailto:foo@example.org -REQUEST-STATUS:5;foo -ATTACH:blabla -END:VEVENT -END:VCALENDAR - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - // vCard 2.1 is not supported yet, so this returns a failure. - - $result = $this->cli->main(array('vobject', 'color', '-')); - - rewind($this->cli->stderr); - $error = stream_get_contents($this->cli->stderr); - - $this->assertEquals( - 0, - $result, - "This should have been error free. stderr output:\n" . $error - ); - - } - - /** - * Note: this is a very shallow test, doesn't dig into the actual output, - * but just makes sure there's no errors thrown. - * - * The colorizer is not a critical component, it's mostly a debugging tool. - */ - function testColorVCard() { - - $inputStream = fopen('php://memory','r+'); - - $version = Version::VERSION; - - /** - * This object is not valid, but it's designed to hit every part of the - * colorizer source. - */ - fwrite($inputStream, <<<VCARD -BEGIN:VCARD -VERSION:4.0 -PRODID:-//Sabre//Sabre VObject {$version}//EN -ADR:1;2;3;4a,4b;5;6 -group.TEL:123454768 -END:VCARD - -VCARD - ); - rewind($inputStream); - $this->cli->stdin = $inputStream; - // vCard 2.1 is not supported yet, so this returns a failure. - - $result = $this->cli->main(array('vobject', 'color', '-')); - - rewind($this->cli->stderr); - $error = stream_get_contents($this->cli->stderr); - - $this->assertEquals( - 0, - $result, - "This should have been error free. stderr output:\n" . $error - ); - - } -} - -class CliMock extends Cli { - - public $log = array(); - - public $quiet = false; - - public $format; - - public $pretty; - - public $stdin; - - public $stdout; - - public $stderr; - - public $inputFormat; - - public $outputFormat; - -}
--- a/vendor/sabre/vobject/tests/VObject/Component/VAlarmTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,179 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject\Component; -use DateTime; -use Sabre\VObject\Reader; - -class VAlarmTest extends \PHPUnit_Framework_TestCase { - - /** - * @dataProvider timeRangeTestData - */ - public function testInTimeRange(VAlarm $valarm,$start,$end,$outcome) { - - $this->assertEquals($outcome, $valarm->isInTimeRange($start, $end)); - - } - - public function timeRangeTestData() { - - $tests = array(); - - $calendar = new VCalendar(); - - // Hard date and time - $valarm1 = $calendar->createComponent('VALARM'); - $valarm1->add( - $calendar->createProperty('TRIGGER', '20120312T130000Z', array('VALUE' => 'DATE-TIME')) - ); - - $tests[] = array($valarm1, new DateTime('2012-03-01 01:00:00'), new DateTime('2012-04-01 01:00:00'), true); - $tests[] = array($valarm1, new DateTime('2012-03-01 01:00:00'), new DateTime('2012-03-10 01:00:00'), false); - - // Relation to start time of event - $valarm2 = $calendar->createComponent('VALARM'); - $valarm2->add( - $calendar->createProperty('TRIGGER', '-P1D', array('VALUE' => 'DURATION')) - ); - - $vevent2 = $calendar->createComponent('VEVENT'); - $vevent2->DTSTART = '20120313T130000Z'; - $vevent2->add($valarm2); - - $tests[] = array($valarm2, new DateTime('2012-03-01 01:00:00'), new DateTime('2012-04-01 01:00:00'), true); - $tests[] = array($valarm2, new DateTime('2012-03-01 01:00:00'), new DateTime('2012-03-10 01:00:00'), false); - - // Relation to end time of event - $valarm3 = $calendar->createComponent('VALARM'); - $valarm3->add( $calendar->createProperty('TRIGGER', '-P1D', array('VALUE'=>'DURATION', 'RELATED' => 'END')) ); - - $vevent3 = $calendar->createComponent('VEVENT'); - $vevent3->DTSTART = '20120301T130000Z'; - $vevent3->DTEND = '20120401T130000Z'; - $vevent3->add($valarm3); - - $tests[] = array($valarm3, new DateTime('2012-02-25 01:00:00'), new DateTime('2012-03-05 01:00:00'), false); - $tests[] = array($valarm3, new DateTime('2012-03-25 01:00:00'), new DateTime('2012-04-05 01:00:00'), true); - - // Relation to end time of todo - $valarm4 = $calendar->createComponent('VALARM'); - $valarm4->TRIGGER = '-P1D'; - $valarm4->TRIGGER['VALUE'] = 'DURATION'; - $valarm4->TRIGGER['RELATED']= 'END'; - - $vtodo4 = $calendar->createComponent('VTODO'); - $vtodo4->DTSTART = '20120301T130000Z'; - $vtodo4->DUE = '20120401T130000Z'; - $vtodo4->add($valarm4); - - $tests[] = array($valarm4, new DateTime('2012-02-25 01:00:00'), new DateTime('2012-03-05 01:00:00'), false); - $tests[] = array($valarm4, new DateTime('2012-03-25 01:00:00'), new DateTime('2012-04-05 01:00:00'), true); - - // Relation to start time of event + repeat - $valarm5 = $calendar->createComponent('VALARM'); - $valarm5->TRIGGER = '-P1D'; - $valarm5->TRIGGER['VALUE'] = 'DURATION'; - $valarm5->REPEAT = 10; - $valarm5->DURATION = 'P1D'; - - $vevent5 = $calendar->createComponent('VEVENT'); - $vevent5->DTSTART = '20120301T130000Z'; - $vevent5->add($valarm5); - - $tests[] = array($valarm5, new DateTime('2012-03-09 01:00:00'), new DateTime('2012-03-10 01:00:00'), true); - - // Relation to start time of event + duration, but no repeat - $valarm6 = $calendar->createComponent('VALARM'); - $valarm6->TRIGGER = '-P1D'; - $valarm6->TRIGGER['VALUE'] = 'DURATION'; - $valarm6->DURATION = 'P1D'; - - $vevent6 = $calendar->createComponent('VEVENT'); - $vevent6->DTSTART = '20120313T130000Z'; - $vevent6->add($valarm6); - - $tests[] = array($valarm6, new DateTime('2012-03-01 01:00:00'), new DateTime('2012-04-01 01:00:00'), true); - $tests[] = array($valarm6, new DateTime('2012-03-01 01:00:00'), new DateTime('2012-03-10 01:00:00'), false); - - - // Relation to end time of event (DURATION instead of DTEND) - $valarm7 = $calendar->createComponent('VALARM'); - $valarm7->TRIGGER = '-P1D'; - $valarm7->TRIGGER['VALUE'] = 'DURATION'; - $valarm7->TRIGGER['RELATED']= 'END'; - - $vevent7 = $calendar->createComponent('VEVENT'); - $vevent7->DTSTART = '20120301T130000Z'; - $vevent7->DURATION = 'P30D'; - $vevent7->add($valarm7); - - $tests[] = array($valarm7, new DateTime('2012-02-25 01:00:00'), new DateTime('2012-03-05 01:00:00'), false); - $tests[] = array($valarm7, new DateTime('2012-03-25 01:00:00'), new DateTime('2012-04-05 01:00:00'), true); - - // Relation to end time of event (No DTEND or DURATION) - $valarm7 = $calendar->createComponent('VALARM'); - $valarm7->TRIGGER = '-P1D'; - $valarm7->TRIGGER['VALUE'] = 'DURATION'; - $valarm7->TRIGGER['RELATED']= 'END'; - - $vevent7 = $calendar->createComponent('VEVENT'); - $vevent7->DTSTART = '20120301T130000Z'; - $vevent7->add($valarm7); - - $tests[] = array($valarm7, new DateTime('2012-02-25 01:00:00'), new DateTime('2012-03-05 01:00:00'), true); - $tests[] = array($valarm7, new DateTime('2012-03-25 01:00:00'), new DateTime('2012-04-05 01:00:00'), false); - - - return $tests; - } - - /** - * @expectedException LogicException - */ - public function testInTimeRangeInvalidComponent() { - - $calendar = new VCalendar(); - $valarm = $calendar->createComponent('VALARM'); - $valarm->TRIGGER = '-P1D'; - $valarm->TRIGGER['RELATED'] = 'END'; - - $vjournal = $calendar->createComponent('VJOURNAL'); - $vjournal->add($valarm); - - $valarm->isInTimeRange(new DateTime('2012-02-25 01:00:00'), new DateTime('2012-03-05 01:00:00')); - - } - - /** - * This bug was found and reported on the mailing list. - */ - public function testInTimeRangeBuggy() { - -$input = <<<BLA -BEGIN:VCALENDAR -BEGIN:VTODO -DTSTAMP:20121003T064931Z -UID:b848cb9a7bb16e464a06c222ca1f8102@examle.com -STATUS:NEEDS-ACTION -DUE:20121005T000000Z -SUMMARY:Task 1 -CATEGORIES:AlarmCategory -BEGIN:VALARM -TRIGGER:-PT10M -ACTION:DISPLAY -DESCRIPTION:Task 1 -END:VALARM -END:VTODO -END:VCALENDAR -BLA; - - $vobj = Reader::read($input); - - $this->assertTrue($vobj->VTODO->VALARM->isInTimeRange(new \DateTime('2012-10-01 00:00:00'), new \DateTime('2012-11-01 00:00:00'))); - - } - -} -
--- a/vendor/sabre/vobject/tests/VObject/Component/VCalendarTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,696 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use DateTimeZone; -use Sabre\VObject; - -class VCalendarTest extends \PHPUnit_Framework_TestCase { - - /** - * @dataProvider expandData - */ - public function testExpand($input, $output, $timeZone = 'UTC', $start = '2011-12-01', $end = '2011-12-31') { - - $vcal = VObject\Reader::read($input); - - $timeZone = new DateTimeZone($timeZone); - - $vcal->expand( - new \DateTime($start), - new \DateTime($end), - $timeZone - ); - - // This will normalize the output - $output = VObject\Reader::read($output)->serialize(); - - $this->assertEquals($output, $vcal->serialize()); - - } - - public function expandData() { - - $tests = array(); - - // No data - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -END:VCALENDAR -'; - - $output = $input; - $tests[] = array($input,$output); - - - // Simple events - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -UID:bla -SUMMARY:InExpand -DTSTART;VALUE=DATE:20111202 -END:VEVENT -BEGIN:VEVENT -UID:bla2 -SUMMARY:NotInExpand -DTSTART;VALUE=DATE:20120101 -END:VEVENT -END:VCALENDAR -'; - - $output = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -UID:bla -SUMMARY:InExpand -DTSTART;VALUE=DATE:20111202 -END:VEVENT -END:VCALENDAR -'; - - $tests[] = array($input, $output); - - // Removing timezone info - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VTIMEZONE -TZID:Europe/Paris -END:VTIMEZONE -BEGIN:VEVENT -UID:bla4 -SUMMARY:RemoveTZ info -DTSTART;TZID=Europe/Paris:20111203T130102 -END:VEVENT -END:VCALENDAR -'; - - $output = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -UID:bla4 -SUMMARY:RemoveTZ info -DTSTART:20111203T120102Z -END:VEVENT -END:VCALENDAR -'; - - $tests[] = array($input, $output); - - // Recurrence rule - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule -DTSTART:20111125T120000Z -DTEND:20111125T130000Z -RRULE:FREQ=WEEKLY -END:VEVENT -END:VCALENDAR -'; - - $output = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule -DTSTART:20111202T120000Z -DTEND:20111202T130000Z -RECURRENCE-ID:20111202T120000Z -END:VEVENT -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule -DTSTART:20111209T120000Z -DTEND:20111209T130000Z -RECURRENCE-ID:20111209T120000Z -END:VEVENT -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule -DTSTART:20111216T120000Z -DTEND:20111216T130000Z -RECURRENCE-ID:20111216T120000Z -END:VEVENT -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule -DTSTART:20111223T120000Z -DTEND:20111223T130000Z -RECURRENCE-ID:20111223T120000Z -END:VEVENT -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule -DTSTART:20111230T120000Z -DTEND:20111230T130000Z -RECURRENCE-ID:20111230T120000Z -END:VEVENT -END:VCALENDAR -'; - - $tests[] = array($input, $output); - - // Recurrence rule + override - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule2 -DTSTART:20111125T120000Z -DTEND:20111125T130000Z -RRULE:FREQ=WEEKLY -END:VEVENT -BEGIN:VEVENT -UID:bla6 -RECURRENCE-ID:20111209T120000Z -DTSTART:20111209T140000Z -DTEND:20111209T150000Z -SUMMARY:Override! -END:VEVENT -END:VCALENDAR -'; - - $output = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule2 -DTSTART:20111202T120000Z -DTEND:20111202T130000Z -RECURRENCE-ID:20111202T120000Z -END:VEVENT -BEGIN:VEVENT -UID:bla6 -RECURRENCE-ID:20111209T120000Z -DTSTART:20111209T140000Z -DTEND:20111209T150000Z -SUMMARY:Override! -END:VEVENT -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule2 -DTSTART:20111216T120000Z -DTEND:20111216T130000Z -RECURRENCE-ID:20111216T120000Z -END:VEVENT -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule2 -DTSTART:20111223T120000Z -DTEND:20111223T130000Z -RECURRENCE-ID:20111223T120000Z -END:VEVENT -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule2 -DTSTART:20111230T120000Z -DTEND:20111230T130000Z -RECURRENCE-ID:20111230T120000Z -END:VEVENT -END:VCALENDAR -'; - - $tests[] = array($input, $output); - - // Floating dates and times. - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:bla1 -DTSTART:20141112T195000 -END:VEVENT -BEGIN:VEVENT -UID:bla2 -DTSTART;VALUE=DATE:20141112 -END:VEVENT -BEGIN:VEVENT -UID:bla3 -DTSTART;VALUE=DATE:20141112 -RRULE:FREQ=DAILY;COUNT=2 -END:VEVENT -END:VCALENDAR -ICS; - - $output = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:bla1 -DTSTART:20141112T225000Z -END:VEVENT -BEGIN:VEVENT -UID:bla2 -DTSTART;VALUE=DATE:20141112 -END:VEVENT -BEGIN:VEVENT -UID:bla3 -DTSTART;VALUE=DATE:20141112 -END:VEVENT -BEGIN:VEVENT -UID:bla3 -DTSTART;VALUE=DATE:20141113 -RECURRENCE-ID;VALUE=DATE:20141113 -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array($input, $output, 'America/Argentina/Buenos_Aires', '2014-01-01', '2015-01-01'); - - // Recurrence rule with no valid instances - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -UID:bla6 -SUMMARY:Testing RRule3 -DTSTART:20111125T120000Z -DTEND:20111125T130000Z -RRULE:FREQ=WEEKLY;COUNT=1 -EXDATE:20111125T120000Z -END:VEVENT -END:VCALENDAR -'; - - $output = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -END:VCALENDAR -'; - - $tests[] = array($input, $output); - return $tests; - - } - - /** - * @expectedException LogicException - */ - public function testBrokenEventExpand() { - - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -RRULE:FREQ=WEEKLY -DTSTART;VALUE=DATE:20111202 -END:VEVENT -END:VCALENDAR -'; - $vcal = VObject\Reader::read($input); - $vcal->expand( - new \DateTime('2011-12-01'), - new \DateTime('2011-12-31') - ); - - } - - function testGetDocumentType() { - - $vcard = new VCalendar(); - $vcard->VERSION = '2.0'; - $this->assertEquals(VCalendar::ICALENDAR20, $vcard->getDocumentType()); - - } - - function testValidateCorrect() { - - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -PRODID:foo -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -DTSTAMP:20140122T233226Z -UID:foo -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - $this->assertEquals(array(), $vcal->validate(), 'Got an error'); - - } - - function testValidateNoVersion() { - - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -PRODID:foo -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - $this->assertEquals(1, count($vcal->validate())); - - } - - function testValidateWrongVersion() { - - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:3.0 -PRODID:foo -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - $this->assertEquals(1, count($vcal->validate())); - - } - - function testValidateNoProdId() { - - $input = 'BEGIN:VCALENDAR -CALSCALE:GREGORIAN -VERSION:2.0 -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - $this->assertEquals(1, count($vcal->validate())); - - } - - function testValidateDoubleCalScale() { - - $input = 'BEGIN:VCALENDAR -VERSION:2.0 -PRODID:foo -CALSCALE:GREGORIAN -CALSCALE:GREGORIAN -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - $this->assertEquals(1, count($vcal->validate())); - - } - - function testValidateDoubleMethod() { - - $input = 'BEGIN:VCALENDAR -VERSION:2.0 -PRODID:foo -METHOD:REQUEST -METHOD:REQUEST -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - $this->assertEquals(1, count($vcal->validate())); - - } - - function testValidateTwoMasterEvents() { - - $input = 'BEGIN:VCALENDAR -VERSION:2.0 -PRODID:foo -METHOD:REQUEST -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - $this->assertEquals(1, count($vcal->validate())); - - } - - function testValidateOneMasterEvent() { - - $input = 'BEGIN:VCALENDAR -VERSION:2.0 -PRODID:foo -METHOD:REQUEST -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -RECURRENCE-ID;VALUE=DATE:20111202 -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - $this->assertEquals(0, count($vcal->validate())); - - } - - function testGetBaseComponent() { - - $input = 'BEGIN:VCALENDAR -VERSION:2.0 -PRODID:foo -METHOD:REQUEST -BEGIN:VEVENT -SUMMARY:test -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -RECURRENCE-ID;VALUE=DATE:20111202 -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - - $result = $vcal->getBaseComponent(); - $this->assertEquals('test', $result->SUMMARY->getValue()); - - } - - function testGetBaseComponentNoResult() { - - $input = 'BEGIN:VCALENDAR -VERSION:2.0 -PRODID:foo -METHOD:REQUEST -BEGIN:VEVENT -SUMMARY:test -RECURRENCE-ID;VALUE=DATE:20111202 -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -END:VEVENT -BEGIN:VEVENT -DTSTART;VALUE=DATE:20111202 -UID:foo -DTSTAMP:20140122T234434Z -RECURRENCE-ID;VALUE=DATE:20111202 -END:VEVENT -END:VCALENDAR -'; - - $vcal = VObject\Reader::read($input); - - $result = $vcal->getBaseComponent(); - $this->assertNull($result); - - } - - function testNoComponents() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:vobject -END:VCALENDAR -ICS; - - $this->assertValidate( - $input, - 0, - 3, - "An iCalendar object must have at least 1 component." - ); - - } - - function testCalDAVNoComponents() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:vobject -BEGIN:VTIMEZONE -TZID:America/Toronto -END:VTIMEZONE -END:VCALENDAR -ICS; - - $this->assertValidate( - $input, - VCalendar::PROFILE_CALDAV, - 3, - "A calendar object on a CalDAV server must have at least 1 component (VTODO, VEVENT, VJOURNAL)." - ); - - } - - function testCalDAVMultiUID() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:vobject -BEGIN:VEVENT -UID:foo -DTSTAMP:20150109T184500Z -DTSTART:20150109T184500Z -END:VEVENT -BEGIN:VEVENT -UID:bar -DTSTAMP:20150109T184500Z -DTSTART:20150109T184500Z -END:VEVENT -END:VCALENDAR -ICS; - - $this->assertValidate( - $input, - VCalendar::PROFILE_CALDAV, - 3, - "A calendar object on a CalDAV server may only have components with the same UID." - ); - - } - - function testCalDAVMultiComponent() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:vobject -BEGIN:VEVENT -UID:foo -RECURRENCE-ID:20150109T185200Z -DTSTAMP:20150109T184500Z -DTSTART:20150109T184500Z -END:VEVENT -BEGIN:VTODO -UID:foo -DTSTAMP:20150109T184500Z -DTSTART:20150109T184500Z -END:VTODO -END:VCALENDAR -ICS; - - $this->assertValidate( - $input, - VCalendar::PROFILE_CALDAV, - 3, - "A calendar object on a CalDAV server may only have 1 type of component (VEVENT, VTODO or VJOURNAL)." - ); - - } - - function testCalDAVMETHOD() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:PUBLISH -PRODID:vobject -BEGIN:VEVENT -UID:foo -RECURRENCE-ID:20150109T185200Z -DTSTAMP:20150109T184500Z -DTSTART:20150109T184500Z -END:VEVENT -END:VCALENDAR -ICS; - - $this->assertValidate( - $input, - VCalendar::PROFILE_CALDAV, - 3, - "A calendar object on a CalDAV server MUST NOT have a METHOD property." - ); - - } - - function assertValidate($ics, $options, $expectedLevel, $expectedMessage = null) { - - $vcal = VObject\Reader::read($ics); - $result = $vcal->validate($options); - - $this->assertValidateResult($result, $expectedLevel, $expectedMessage); - - } - - function assertValidateResult($input, $expectedLevel, $expectedMessage = null) { - - $messages = array(); - foreach($input as $warning) { - $messages[] = $warning['message']; - } - - if ($expectedLevel === 0) { - $this->assertEquals(0, count($input), 'No validation messages were expected. We got: ' . implode(', ', $messages)); - } else { - $this->assertEquals(1, count($input), 'We expected exactly 1 validation message, We got: ' . implode(', ', $messages)); - - $this->assertEquals($expectedMessage, $input[0]['message']); - $this->assertEquals($expectedLevel, $input[0]['level']); - } - - } - - -}
--- a/vendor/sabre/vobject/tests/VObject/Component/VCardTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,288 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -class VCardTest extends \PHPUnit_Framework_TestCase { - - /** - * @dataProvider validateData - */ - function testValidate($input, $expectedWarnings, $expectedRepairedOutput) { - - $vcard = VObject\Reader::read($input); - - $warnings = $vcard->validate(); - - $warnMsg = array(); - foreach($warnings as $warning) { - $warnMsg[] = $warning['message']; - } - - $this->assertEquals($expectedWarnings, $warnMsg); - - $vcard->validate(VObject\Component::REPAIR); - - $this->assertEquals( - $expectedRepairedOutput, - $vcard->serialize() - ); - - } - - public function validateData() { - - $tests = array(); - - // Correct - $tests[] = array( - "BEGIN:VCARD\r\nVERSION:4.0\r\nFN:John Doe\r\nUID:foo\r\nEND:VCARD\r\n", - array(), - "BEGIN:VCARD\r\nVERSION:4.0\r\nFN:John Doe\r\nUID:foo\r\nEND:VCARD\r\n", - ); - - // No VERSION - $tests[] = array( - "BEGIN:VCARD\r\nFN:John Doe\r\nUID:foo\r\nEND:VCARD\r\n", - array( - 'VERSION MUST appear exactly once in a VCARD component', - ), - "BEGIN:VCARD\r\nVERSION:3.0\r\nFN:John Doe\r\nUID:foo\r\nEND:VCARD\r\n", - ); - - // Unknown version - $tests[] = array( - "BEGIN:VCARD\r\nVERSION:2.2\r\nFN:John Doe\r\nUID:foo\r\nEND:VCARD\r\n", - array( - 'Only vcard version 4.0 (RFC6350), version 3.0 (RFC2426) or version 2.1 (icm-vcard-2.1) are supported.', - ), - "BEGIN:VCARD\r\nVERSION:2.1\r\nFN:John Doe\r\nUID:foo\r\nEND:VCARD\r\n", - ); - - // No FN - $tests[] = array( - "BEGIN:VCARD\r\nVERSION:4.0\r\nUID:foo\r\nEND:VCARD\r\n", - array( - 'The FN property must appear in the VCARD component exactly 1 time', - ), - "BEGIN:VCARD\r\nVERSION:4.0\r\nUID:foo\r\nEND:VCARD\r\n", - ); - // No FN, N fallback - $tests[] = array( - "BEGIN:VCARD\r\nVERSION:4.0\r\nUID:foo\r\nN:Doe;John;;;;;\r\nEND:VCARD\r\n", - array( - 'The FN property must appear in the VCARD component exactly 1 time', - ), - "BEGIN:VCARD\r\nVERSION:4.0\r\nUID:foo\r\nN:Doe;John;;;;;\r\nFN:John Doe\r\nEND:VCARD\r\n", - ); - // No FN, N fallback, no first name - $tests[] = array( - "BEGIN:VCARD\r\nVERSION:4.0\r\nUID:foo\r\nN:Doe;;;;;;\r\nEND:VCARD\r\n", - array( - 'The FN property must appear in the VCARD component exactly 1 time', - ), - "BEGIN:VCARD\r\nVERSION:4.0\r\nUID:foo\r\nN:Doe;;;;;;\r\nFN:Doe\r\nEND:VCARD\r\n", - ); - - // No FN, ORG fallback - $tests[] = array( - "BEGIN:VCARD\r\nVERSION:4.0\r\nUID:foo\r\nORG:Acme Co.\r\nEND:VCARD\r\n", - array( - 'The FN property must appear in the VCARD component exactly 1 time', - ), - "BEGIN:VCARD\r\nVERSION:4.0\r\nUID:foo\r\nORG:Acme Co.\r\nFN:Acme Co.\r\nEND:VCARD\r\n", - ); - return $tests; - - } - - function testGetDocumentType() { - - $vcard = new VCard(array(), false); - $vcard->VERSION = '2.1'; - $this->assertEquals(VCard::VCARD21, $vcard->getDocumentType()); - - $vcard = new VCard(array(), false); - $vcard->VERSION = '3.0'; - $this->assertEquals(VCard::VCARD30, $vcard->getDocumentType()); - - $vcard = new VCard(array(), false); - $vcard->VERSION = '4.0'; - $this->assertEquals(VCard::VCARD40, $vcard->getDocumentType()); - - $vcard = new VCard(array(), false); - $this->assertEquals(VCard::UNKNOWN, $vcard->getDocumentType()); - } - - function testPreferredNoPref() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:3.0 -EMAIL:1@example.org -EMAIL:2@example.org -END:VCARD -VCF; - - $vcard = VObject\Reader::read($vcard); - $this->assertEquals('1@example.org', $vcard->preferred('EMAIL')->getValue()); - - } - - function testPreferredWithPref() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:3.0 -EMAIL:1@example.org -EMAIL;TYPE=PREF:2@example.org -END:VCARD -VCF; - - $vcard = VObject\Reader::read($vcard); - $this->assertEquals('2@example.org', $vcard->preferred('EMAIL')->getValue()); - - } - - function testPreferredWith40Pref() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:4.0 -EMAIL:1@example.org -EMAIL;PREF=3:2@example.org -EMAIL;PREF=2:3@example.org -END:VCARD -VCF; - - $vcard = VObject\Reader::read($vcard); - $this->assertEquals('3@example.org', $vcard->preferred('EMAIL')->getValue()); - - } - - function testPreferredNotFound() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:4.0 -END:VCARD -VCF; - - $vcard = VObject\Reader::read($vcard); - $this->assertNull($vcard->preferred('EMAIL')); - - } - - function testNoUIDCardDAV() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:4.0 -FN:John Doe -END:VCARD -VCF; - $this->assertValidate( - $vcard, - VCARD::PROFILE_CARDDAV, - 3, - 'vCards on CardDAV servers MUST have a UID property.' - ); - - } - - function testNoUIDNoCardDAV() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:4.0 -FN:John Doe -END:VCARD -VCF; - $this->assertValidate( - $vcard, - 0, - 2, - 'Adding a UID to a vCard property is recommended.' - ); - - } - function testNoUIDNoCardDAVRepair() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:4.0 -FN:John Doe -END:VCARD -VCF; - $this->assertValidate( - $vcard, - VCARD::REPAIR, - 1, - 'Adding a UID to a vCard property is recommended.' - ); - - } - - function testVCard21CardDAV() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:2.1 -FN:John Doe -UID:foo -END:VCARD -VCF; - $this->assertValidate( - $vcard, - VCARD::PROFILE_CARDDAV, - 3, - 'CardDAV servers are not allowed to accept vCard 2.1.' - ); - - } - - function testVCard21NoCardDAV() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:2.1 -FN:John Doe -UID:foo -END:VCARD -VCF; - $this->assertValidate( - $vcard, - 0, - 0 - ); - - } - - function assertValidate($vcf, $options, $expectedLevel, $expectedMessage = null) { - - $vcal = VObject\Reader::read($vcf); - $result = $vcal->validate($options); - - $this->assertValidateResult($result, $expectedLevel, $expectedMessage); - - } - - function assertValidateResult($input, $expectedLevel, $expectedMessage = null) { - - $messages = array(); - foreach($input as $warning) { - $messages[] = $warning['message']; - } - - if ($expectedLevel === 0) { - $this->assertEquals(0, count($input), 'No validation messages were expected. We got: ' . implode(', ', $messages)); - } else { - $this->assertEquals(1, count($input), 'We expected exactly 1 validation message, We got: ' . implode(', ', $messages)); - - $this->assertEquals($expectedMessage, $input[0]['message']); - $this->assertEquals($expectedLevel, $input[0]['level']); - } - - } -}
--- a/vendor/sabre/vobject/tests/VObject/Component/VEventTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,76 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; - -class VEventTest extends \PHPUnit_Framework_TestCase { - - /** - * @dataProvider timeRangeTestData - */ - public function testInTimeRange(VEvent $vevent,$start,$end,$outcome) { - - $this->assertEquals($outcome, $vevent->isInTimeRange($start, $end)); - - } - - public function timeRangeTestData() { - - $tests = array(); - - $calendar = new VCalendar(); - - $vevent = $calendar->createComponent('VEVENT'); - $vevent->DTSTART = '20111223T120000Z'; - $tests[] = array($vevent, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vevent, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vevent2 = clone $vevent; - $vevent2->DTEND = '20111225T120000Z'; - $tests[] = array($vevent2, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vevent2, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vevent3 = clone $vevent; - $vevent3->DURATION = 'P1D'; - $tests[] = array($vevent3, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vevent3, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vevent4 = clone $vevent; - $vevent4->DTSTART = '20111225'; - $vevent4->DTSTART['VALUE'] = 'DATE'; - $tests[] = array($vevent4, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vevent4, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - // Event with no end date should be treated as lasting the entire day. - $tests[] = array($vevent4, new \DateTime('2011-12-25 16:00:00'), new \DateTime('2011-12-25 17:00:00'), true); - - - $vevent5 = clone $vevent; - $vevent5->DURATION = 'P1D'; - $vevent5->RRULE = 'FREQ=YEARLY'; - $tests[] = array($vevent5, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vevent5, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - $tests[] = array($vevent5, new \DateTime('2013-12-01'), new \DateTime('2013-12-31'), true); - - $vevent6 = clone $vevent; - $vevent6->DTSTART = '20111225'; - $vevent6->DTSTART['VALUE'] = 'DATE'; - $vevent6->DTEND = '20111225'; - $vevent6->DTEND['VALUE'] = 'DATE'; - - $tests[] = array($vevent6, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vevent6, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - // Added this test to ensure that recurrence rules with no DTEND also - // get checked for the entire day. - $vevent7 = clone $vevent; - $vevent7->DTSTART = '20120101'; - $vevent7->DTSTART['VALUE'] = 'DATE'; - $vevent7->RRULE = 'FREQ=MONTHLY'; - $tests[] = array($vevent7, new \DateTime('2012-02-01 15:00:00'), new \DateTime('2012-02-02'), true); - return $tests; - - } - -} -
--- a/vendor/sabre/vobject/tests/VObject/Component/VFreeBusyTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,66 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; -use Sabre\VObject\Reader; - -class VFreeBusyTest extends \PHPUnit_Framework_TestCase { - - function testIsFree() { - - $input = <<<BLA -BEGIN:VCALENDAR -BEGIN:VFREEBUSY -FREEBUSY;FBTYPE=FREE:20120912T000500Z/PT1H -FREEBUSY;FBTYPE=BUSY:20120912T010000Z/20120912T020000Z -FREEBUSY;FBTYPE=BUSY-TENTATIVE:20120912T020000Z/20120912T030000Z -FREEBUSY;FBTYPE=BUSY-UNAVAILABLE:20120912T030000Z/20120912T040000Z -FREEBUSY;FBTYPE=BUSY:20120912T050000Z/20120912T060000Z,20120912T080000Z/20120912T090000Z -FREEBUSY;FBTYPE=BUSY:20120912T100000Z/PT1H -END:VFREEBUSY -END:VCALENDAR -BLA; - - $obj = VObject\Reader::read($input); - $vfb = $obj->VFREEBUSY; - - $tz = new \DateTimeZone('UTC'); - - $this->assertFalse($vfb->isFree(new \DateTime('2012-09-12 01:15:00', $tz), new \DateTime('2012-09-12 01:45:00', $tz))); - $this->assertFalse($vfb->isFree(new \DateTime('2012-09-12 08:05:00', $tz), new \DateTime('2012-09-12 08:10:00', $tz))); - $this->assertFalse($vfb->isFree(new \DateTime('2012-09-12 10:15:00', $tz), new \DateTime('2012-09-12 10:45:00', $tz))); - - // Checking whether the end time is treated as non-inclusive - $this->assertTrue($vfb->isFree(new \DateTime('2012-09-12 09:00:00', $tz), new \DateTime('2012-09-12 09:15:00', $tz))); - $this->assertTrue($vfb->isFree(new \DateTime('2012-09-12 09:45:00', $tz), new \DateTime('2012-09-12 10:00:00', $tz))); - $this->assertTrue($vfb->isFree(new \DateTime('2012-09-12 11:00:00', $tz), new \DateTime('2012-09-12 12:00:00', $tz))); - - } - - public function testValidate() { - - $input = <<<HI -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:YoYo -BEGIN:VFREEBUSY -UID:some-random-id -DTSTAMP:20140402T180200Z -END:VFREEBUSY -END:VCALENDAR -HI; - - $obj = Reader::read($input); - - $warnings = $obj->validate(); - $messages = array(); - foreach($warnings as $warning) { - $messages[] = $warning['message']; - } - - $this->assertEquals(array(), $messages); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Component/VJournalTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,101 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject\Component; -use Sabre\VObject\Reader; - -class VJournalTest extends \PHPUnit_Framework_TestCase { - - /** - * @dataProvider timeRangeTestData - */ - public function testInTimeRange(VJournal $vtodo,$start,$end,$outcome) { - - $this->assertEquals($outcome, $vtodo->isInTimeRange($start, $end)); - - } - - public function testValidate() { - - $input = <<<HI -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:YoYo -BEGIN:VJOURNAL -UID:12345678 -DTSTAMP:20140402T174100Z -END:VJOURNAL -END:VCALENDAR -HI; - - $obj = Reader::read($input); - - $warnings = $obj->validate(); - $messages = array(); - foreach($warnings as $warning) { - $messages[] = $warning['message']; - } - - $this->assertEquals(array(), $messages); - - } - - public function testValidateBroken() { - - $input = <<<HI -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:YoYo -BEGIN:VJOURNAL -UID:12345678 -DTSTAMP:20140402T174100Z -URL:http://example.org/ -URL:http://example.com/ -END:VJOURNAL -END:VCALENDAR -HI; - - $obj = Reader::read($input); - - $warnings = $obj->validate(); - $messages = array(); - foreach($warnings as $warning) { - $messages[] = $warning['message']; - } - - $this->assertEquals( - array("URL MUST NOT appear more than once in a VJOURNAL component"), - $messages - ); - - } - - public function timeRangeTestData() { - - $calendar = new VCalendar(); - - $tests = array(); - - $vjournal = $calendar->createComponent('VJOURNAL'); - $vjournal->DTSTART = '20111223T120000Z'; - $tests[] = array($vjournal, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vjournal, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vjournal2 = $calendar->createComponent('VJOURNAL'); - $vjournal2->DTSTART = '20111223'; - $vjournal2->DTSTART['VALUE'] = 'DATE'; - $tests[] = array($vjournal2, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vjournal2, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vjournal3 = $calendar->createComponent('VJOURNAL'); - $tests[] = array($vjournal3, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), false); - $tests[] = array($vjournal3, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - return $tests; - } - - - -} -
--- a/vendor/sabre/vobject/tests/VObject/Component/VTimeZoneTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,57 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use Sabre\VObject; -use Sabre\VObject\Reader; - -class VTimeZoneTest extends \PHPUnit_Framework_TestCase { - - function testValidate() { - - $input = <<<HI -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:YoYo -BEGIN:VTIMEZONE -TZID:America/Toronto -END:VTIMEZONE -END:VCALENDAR -HI; - - $obj = Reader::read($input); - - $warnings = $obj->validate(); - $messages = array(); - foreach($warnings as $warning) { - $messages[] = $warning['message']; - } - - $this->assertEquals(array(), $messages); - - } - - function testGetTimeZone() { - - $input = <<<HI -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:YoYo -BEGIN:VTIMEZONE -TZID:America/Toronto -END:VTIMEZONE -END:VCALENDAR -HI; - - $obj = Reader::read($input); - - $tz = new \DateTimeZone('America/Toronto'); - - $this->assertEquals( - $tz, - $obj->VTIMEZONE->getTimeZone() - ); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Component/VTodoTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,180 +0,0 @@ -<?php - -namespace Sabre\VObject\Component; - -use - Sabre\VObject\Component, - Sabre\VObject\Reader; - -class VTodoTest extends \PHPUnit_Framework_TestCase { - - /** - * @dataProvider timeRangeTestData - */ - public function testInTimeRange(VTodo $vtodo,$start,$end,$outcome) { - - $this->assertEquals($outcome, $vtodo->isInTimeRange($start, $end)); - - } - - public function timeRangeTestData() { - - $tests = array(); - - $calendar = new VCalendar(); - - $vtodo = $calendar->createComponent('VTODO'); - $vtodo->DTSTART = '20111223T120000Z'; - $tests[] = array($vtodo, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vtodo, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vtodo2 = clone $vtodo; - $vtodo2->DURATION = 'P1D'; - $tests[] = array($vtodo2, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vtodo2, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vtodo3 = clone $vtodo; - $vtodo3->DUE = '20111225'; - $tests[] = array($vtodo3, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vtodo3, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vtodo4 = $calendar->createComponent('VTODO'); - $vtodo4->DUE = '20111225'; - $tests[] = array($vtodo4, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vtodo4, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vtodo5 = $calendar->createComponent('VTODO'); - $vtodo5->COMPLETED = '20111225'; - $tests[] = array($vtodo5, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vtodo5, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vtodo6 = $calendar->createComponent('VTODO'); - $vtodo6->CREATED = '20111225'; - $tests[] = array($vtodo6, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vtodo6, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vtodo7 = $calendar->createComponent('VTODO'); - $vtodo7->CREATED = '20111225'; - $vtodo7->COMPLETED = '20111226'; - $tests[] = array($vtodo7, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vtodo7, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), false); - - $vtodo7 = $calendar->createComponent('VTODO'); - $tests[] = array($vtodo7, new \DateTime('2011-01-01'), new \DateTime('2012-01-01'), true); - $tests[] = array($vtodo7, new \DateTime('2011-01-01'), new \DateTime('2011-11-01'), true); - - return $tests; - - } - - public function testValidate() { - - $input = <<<HI -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:YoYo -BEGIN:VTODO -UID:1234-21355-123156 -DTSTAMP:20140402T183400Z -END:VTODO -END:VCALENDAR -HI; - - $obj = Reader::read($input); - - $warnings = $obj->validate(); - $messages = array(); - foreach($warnings as $warning) { - $messages[] = $warning['message']; - } - - $this->assertEquals(array(), $messages); - - } - - public function testValidateInvalid() { - - $input = <<<HI -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:YoYo -BEGIN:VTODO -END:VTODO -END:VCALENDAR -HI; - - $obj = Reader::read($input); - - $warnings = $obj->validate(); - $messages = array(); - foreach($warnings as $warning) { - $messages[] = $warning['message']; - } - - $this->assertEquals(array( - "UID MUST appear exactly once in a VTODO component", - "DTSTAMP MUST appear exactly once in a VTODO component", - ), $messages); - - } - - public function testValidateDUEDTSTARTMisMatch() { - - $input = <<<HI -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:YoYo -BEGIN:VTODO -UID:FOO -DTSTART;VALUE=DATE-TIME:20140520T131600Z -DUE;VALUE=DATE:20140520 -DTSTAMP;VALUE=DATE-TIME:20140520T131600Z -END:VTODO -END:VCALENDAR -HI; - - $obj = Reader::read($input); - - $warnings = $obj->validate(); - $messages = array(); - foreach($warnings as $warning) { - $messages[] = $warning['message']; - } - - $this->assertEquals(array( - "The value type (DATE or DATE-TIME) must be identical for DUE and DTSTART", - ), $messages); - - } - - public function testValidateDUEbeforeDTSTART() { - - $input = <<<HI -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:YoYo -BEGIN:VTODO -UID:FOO -DTSTART;VALUE=DATE:20140520 -DUE;VALUE=DATE:20140518 -DTSTAMP;VALUE=DATE-TIME:20140520T131600Z -END:VTODO -END:VCALENDAR -HI; - - $obj = Reader::read($input); - - $warnings = $obj->validate(); - $messages = array(); - foreach($warnings as $warning) { - $messages[] = $warning['message']; - } - - $this->assertEquals(array( - "DUE must occur after DTSTART", - ), $messages); - - } - -} -
--- a/vendor/sabre/vobject/tests/VObject/ComponentTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,528 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - Sabre\VObject\Component\VCalendar, - Sabre\VObject\Component\VCard; - -class ComponentTest extends \PHPUnit_Framework_TestCase { - - function testIterate() { - - $comp = new VCalendar(array(), false); - - $sub = $comp->createComponent('VEVENT'); - $comp->add($sub); - - $sub = $comp->createComponent('VTODO'); - $comp->add($sub); - - $count = 0; - foreach($comp->children() as $key=>$subcomponent) { - - $count++; - $this->assertInstanceOf('Sabre\\VObject\\Component',$subcomponent); - - } - $this->assertEquals(2,$count); - $this->assertEquals(1,$key); - - } - - function testMagicGet() { - - $comp = new VCalendar(array(), false); - - $sub = $comp->createComponent('VEVENT'); - $comp->add($sub); - - $sub = $comp->createComponent('VTODO'); - $comp->add($sub); - - $event = $comp->vevent; - $this->assertInstanceOf('Sabre\\VObject\\Component', $event); - $this->assertEquals('VEVENT', $event->name); - - $this->assertInternalType('null', $comp->vjournal); - - } - - function testMagicGetGroups() { - - $comp = new VCard(); - - $sub = $comp->createProperty('GROUP1.EMAIL','1@1.com'); - $comp->add($sub); - - $sub = $comp->createProperty('GROUP2.EMAIL','2@2.com'); - $comp->add($sub); - - $sub = $comp->createProperty('EMAIL','3@3.com'); - $comp->add($sub); - - $emails = $comp->email; - $this->assertEquals(3, count($emails)); - - $email1 = $comp->{"group1.email"}; - $this->assertEquals('EMAIL', $email1[0]->name); - $this->assertEquals('GROUP1', $email1[0]->group); - - $email3 = $comp->{".email"}; - $this->assertEquals('EMAIL', $email3[0]->name); - $this->assertEquals(null, $email3[0]->group); - - } - - function testMagicIsset() { - - $comp = new VCalendar(); - - $sub = $comp->createComponent('VEVENT'); - $comp->add($sub); - - $sub = $comp->createComponent('VTODO'); - $comp->add($sub); - - $this->assertTrue(isset($comp->vevent)); - $this->assertTrue(isset($comp->vtodo)); - $this->assertFalse(isset($comp->vjournal)); - - } - - function testMagicSetScalar() { - - $comp = new VCalendar(); - $comp->myProp = 'myValue'; - - $this->assertInstanceOf('Sabre\\VObject\\Property',$comp->MYPROP); - $this->assertEquals('myValue',(string)$comp->MYPROP); - - - } - - function testMagicSetScalarTwice() { - - $comp = new VCalendar(array(), false); - $comp->myProp = 'myValue'; - $comp->myProp = 'myValue'; - - $this->assertEquals(1,count($comp->children())); - $this->assertInstanceOf('Sabre\\VObject\\Property',$comp->MYPROP); - $this->assertEquals('myValue',(string)$comp->MYPROP); - - } - - function testMagicSetArray() { - - $comp = new VCalendar(); - $comp->ORG = array('Acme Inc', 'Section 9'); - - $this->assertInstanceOf('Sabre\\VObject\\Property',$comp->ORG); - $this->assertEquals(array('Acme Inc', 'Section 9'),$comp->ORG->getParts()); - - } - - function testMagicSetComponent() { - - $comp = new VCalendar(); - - // Note that 'myProp' is ignored here. - $comp->myProp = $comp->createComponent('VEVENT'); - - $this->assertEquals(1, count($comp)); - - $this->assertEquals('VEVENT',$comp->VEVENT->name); - - } - - function testMagicSetTwice() { - - $comp = new VCalendar(array(), false); - - $comp->VEVENT = $comp->createComponent('VEVENT'); - $comp->VEVENT = $comp->createComponent('VEVENT'); - - $this->assertEquals(1, count($comp->children())); - - $this->assertEquals('VEVENT',$comp->VEVENT->name); - - } - - function testArrayAccessGet() { - - $comp = new VCalendar(array(), false); - - $event = $comp->createComponent('VEVENT'); - $event->summary = 'Event 1'; - - $comp->add($event); - - $event2 = clone $event; - $event2->summary = 'Event 2'; - - $comp->add($event2); - - $this->assertEquals(2,count($comp->children())); - $this->assertTrue($comp->vevent[1] instanceof Component); - $this->assertEquals('Event 2', (string)$comp->vevent[1]->summary); - - } - - function testArrayAccessExists() { - - $comp = new VCalendar(); - - $event = $comp->createComponent('VEVENT'); - $event->summary = 'Event 1'; - - $comp->add($event); - - $event2 = clone $event; - $event2->summary = 'Event 2'; - - $comp->add($event2); - - $this->assertTrue(isset($comp->vevent[0])); - $this->assertTrue(isset($comp->vevent[1])); - - } - - /** - * @expectedException LogicException - */ - function testArrayAccessSet() { - - $comp = new VCalendar(); - $comp['hey'] = 'hi there'; - - } - /** - * @expectedException LogicException - */ - function testArrayAccessUnset() { - - $comp = new VCalendar(); - unset($comp[0]); - - } - - function testAddScalar() { - - $comp = new VCalendar(array(), false); - - $comp->add('myprop','value'); - - $this->assertEquals(1, count($comp->children())); - - $bla = $comp->children[0]; - - $this->assertTrue($bla instanceof Property); - $this->assertEquals('MYPROP',$bla->name); - $this->assertEquals('value',(string)$bla); - - } - - function testAddScalarParams() { - - $comp = new VCalendar(array(), false); - - $comp->add('myprop','value',array('param1'=>'value1')); - - $this->assertEquals(1, count($comp->children())); - - $bla = $comp->children[0]; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $bla); - $this->assertEquals('MYPROP',$bla->name); - $this->assertEquals('value', (string)$bla); - - $this->assertEquals(1, count($bla->parameters())); - - $this->assertEquals('PARAM1',$bla->parameters['PARAM1']->name); - $this->assertEquals('value1',$bla->parameters['PARAM1']->getValue()); - - } - - - function testAddComponent() { - - $comp = new VCalendar(array(), false); - - $comp->add($comp->createComponent('VEVENT')); - - $this->assertEquals(1, count($comp->children())); - - $this->assertEquals('VEVENT',$comp->VEVENT->name); - - } - - function testAddComponentTwice() { - - $comp = new VCalendar(array(), false); - - $comp->add($comp->createComponent('VEVENT')); - $comp->add($comp->createComponent('VEVENT')); - - $this->assertEquals(2, count($comp->children())); - - $this->assertEquals('VEVENT',$comp->VEVENT->name); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testAddArgFail() { - - $comp = new VCalendar(); - $comp->add($comp->createComponent('VEVENT'),'hello'); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testAddArgFail2() { - - $comp = new VCalendar(); - $comp->add(array()); - - } - - function testMagicUnset() { - - $comp = new VCalendar(array(), false); - $comp->add($comp->createComponent('VEVENT')); - - unset($comp->vevent); - - $this->assertEquals(0, count($comp->children())); - - } - - - function testCount() { - - $comp = new VCalendar(); - $this->assertEquals(1,$comp->count()); - - } - - function testChildren() { - - $comp = new VCalendar(array(), false); - - // Note that 'myProp' is ignored here. - $comp->add($comp->createComponent('VEVENT')); - $comp->add($comp->createComponent('VTODO')); - - $r = $comp->children(); - $this->assertInternalType('array', $r); - $this->assertEquals(2,count($r)); - } - - function testGetComponents() { - - $comp = new VCalendar(); - - $comp->add($comp->createProperty('FOO','BAR')); - $comp->add($comp->createComponent('VTODO')); - - $r = $comp->getComponents(); - $this->assertInternalType('array', $r); - $this->assertEquals(1, count($r)); - $this->assertEquals('VTODO', $r[0]->name); - } - - function testSerialize() { - - $comp = new VCalendar(array(), false); - $this->assertEquals("BEGIN:VCALENDAR\r\nEND:VCALENDAR\r\n", $comp->serialize()); - - } - - function testSerializeChildren() { - - $comp = new VCalendar(array(), false); - $event = $comp->add($comp->createComponent('VEVENT')); - unset($event->DTSTAMP, $event->UID); - $comp->add($comp->createComponent('VTODO')); - - $str = $comp->serialize(); - - $this->assertEquals("BEGIN:VCALENDAR\r\nBEGIN:VEVENT\r\nEND:VEVENT\r\nBEGIN:VTODO\r\nEND:VTODO\r\nEND:VCALENDAR\r\n", $str); - - } - - function testSerializeOrderCompAndProp() { - - $comp = new VCalendar(array(), false); - $comp->add($event = $comp->createComponent('VEVENT')); - $comp->add('PROP1','BLABLA'); - $comp->add('VERSION','2.0'); - $comp->add($comp->createComponent('VTIMEZONE')); - - unset($event->DTSTAMP, $event->UID); - $str = $comp->serialize(); - - $this->assertEquals("BEGIN:VCALENDAR\r\nVERSION:2.0\r\nPROP1:BLABLA\r\nBEGIN:VTIMEZONE\r\nEND:VTIMEZONE\r\nBEGIN:VEVENT\r\nEND:VEVENT\r\nEND:VCALENDAR\r\n", $str); - - } - - function testAnotherSerializeOrderProp() { - - $prop4s=array('1', '2', '3', '4', '5', '6', '7', '8', '9', '10'); - - $comp = new VCard(array(), false); - - $comp->__set('SOMEPROP','FOO'); - $comp->__set('ANOTHERPROP','FOO'); - $comp->__set('THIRDPROP','FOO'); - foreach ($prop4s as $prop4) { - $comp->add('PROP4', 'FOO '.$prop4); - } - $comp->__set('PROPNUMBERFIVE', 'FOO'); - $comp->__set('PROPNUMBERSIX', 'FOO'); - $comp->__set('PROPNUMBERSEVEN', 'FOO'); - $comp->__set('PROPNUMBEREIGHT', 'FOO'); - $comp->__set('PROPNUMBERNINE', 'FOO'); - $comp->__set('PROPNUMBERTEN', 'FOO'); - $comp->__set('VERSION','2.0'); - $comp->__set('UID', 'FOO'); - - $str = $comp->serialize(); - - $this->assertEquals("BEGIN:VCARD\r\nVERSION:2.0\r\nSOMEPROP:FOO\r\nANOTHERPROP:FOO\r\nTHIRDPROP:FOO\r\nPROP4:FOO 1\r\nPROP4:FOO 2\r\nPROP4:FOO 3\r\nPROP4:FOO 4\r\nPROP4:FOO 5\r\nPROP4:FOO 6\r\nPROP4:FOO 7\r\nPROP4:FOO 8\r\nPROP4:FOO 9\r\nPROP4:FOO 10\r\nPROPNUMBERFIVE:FOO\r\nPROPNUMBERSIX:FOO\r\nPROPNUMBERSEVEN:FOO\r\nPROPNUMBEREIGHT:FOO\r\nPROPNUMBERNINE:FOO\r\nPROPNUMBERTEN:FOO\r\nUID:FOO\r\nEND:VCARD\r\n", $str); - - } - - function testInstantiateWithChildren() { - - $comp = new VCard(array( - 'ORG' => array('Acme Inc.', 'Section 9'), - 'FN' => 'Finn The Human', - )); - - $this->assertEquals(array('Acme Inc.', 'Section 9'), $comp->ORG->getParts()); - $this->assertEquals('Finn The Human', $comp->FN->getValue()); - - } - - function testInstantiateSubComponent() { - - $comp = new VCalendar(); - $event = $comp->createComponent('VEVENT', array( - $comp->createProperty('UID', '12345'), - )); - $comp->add($event); - - $this->assertEquals('12345', $comp->VEVENT->UID->getValue()); - - } - - function testRemoveByName() { - - $comp = new VCalendar(array(), false); - $comp->add('prop1','val1'); - $comp->add('prop2','val2'); - $comp->add('prop2','val2'); - - $comp->remove('prop2'); - $this->assertFalse(isset($comp->prop2)); - $this->assertTrue(isset($comp->prop1)); - - } - - function testRemoveByObj() { - - $comp = new VCalendar(array(), false); - $comp->add('prop1','val1'); - $prop = $comp->add('prop2','val2'); - - $comp->remove($prop); - $this->assertFalse(isset($comp->prop2)); - $this->assertTrue(isset($comp->prop1)); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testRemoveNotFound() { - - $comp = new VCalendar(array(), false); - $prop = $comp->createProperty('A','B'); - $comp->remove($prop); - - } - - /** - * @dataProvider ruleData - */ - function testValidateRules($componentList, $errorCount) { - - $vcard = new Component\VCard(); - - $component = new FakeComponent($vcard,'Hi', array(), $defaults = false ); - foreach($componentList as $v) { - $component->add($v,'Hello.'); - } - - $this->assertEquals($errorCount, count($component->validate())); - - } - - function testValidateRepair() { - - $vcard = new Component\VCard(); - - $component = new FakeComponent($vcard,'Hi', array(), $defaults = false ); - $component->validate(Component::REPAIR); - $this->assertEquals('yow', $component->BAR->getValue()); - - } - - function ruleData() { - - return array( - - array(array(), 2), - array(array('FOO'), 3), - array(array('BAR'), 1), - array(array('BAZ'), 1), - array(array('BAR','BAZ'), 0), - array(array('BAR','BAZ','ZIM',), 0), - array(array('BAR','BAZ','ZIM','GIR'), 0), - array(array('BAR','BAZ','ZIM','GIR','GIR'), 1), - - ); - - } - -} - -class FakeComponent extends Component { - - public function getValidationRules() { - - return array( - 'FOO' => '0', - 'BAR' => '1', - 'BAZ' => '+', - 'ZIM' => '*', - 'GIR' => '?', - ); - - } - - public function getDefaults() { - - return array( - 'BAR' => 'yow', - ); - - } - -} -
--- a/vendor/sabre/vobject/tests/VObject/DateTimeParserTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,389 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use DateTime; -use DateTimeZone; -use DateInterval; - -class DateTimeParserTest extends \PHPUnit_Framework_TestCase { - - function testParseICalendarDuration() { - - $this->assertEquals('+1 weeks', DateTimeParser::parseDuration('P1W',true)); - $this->assertEquals('+5 days', DateTimeParser::parseDuration('P5D',true)); - $this->assertEquals('+5 days 3 hours 50 minutes 12 seconds', DateTimeParser::parseDuration('P5DT3H50M12S',true)); - $this->assertEquals('-1 weeks 50 minutes', DateTimeParser::parseDuration('-P1WT50M',true)); - $this->assertEquals('+50 days 3 hours 2 seconds', DateTimeParser::parseDuration('+P50DT3H2S',true)); - $this->assertEquals('+0 seconds', DateTimeParser::parseDuration('+PT0S',true)); - $this->assertEquals(new DateInterval('PT0S'), DateTimeParser::parseDuration('PT0S')); - - } - - function testParseICalendarDurationDateInterval() { - - $expected = new DateInterval('P7D'); - $this->assertEquals($expected, DateTimeParser::parseDuration('P1W')); - $this->assertEquals($expected, DateTimeParser::parse('P1W')); - - $expected = new DateInterval('PT3M'); - $expected->invert = true; - $this->assertEquals($expected, DateTimeParser::parseDuration('-PT3M')); - - } - - /** - * @expectedException LogicException - */ - function testParseICalendarDurationFail() { - - DateTimeParser::parseDuration('P1X',true); - - } - - function testParseICalendarDateTime() { - - $dateTime = DateTimeParser::parseDateTime('20100316T141405'); - - $compare = new DateTime('2010-03-16 14:14:05',new DateTimeZone('UTC')); - - $this->assertEquals($compare, $dateTime); - - } - - /** - * @depends testParseICalendarDateTime - * @expectedException LogicException - */ - function testParseICalendarDateTimeBadFormat() { - - $dateTime = DateTimeParser::parseDateTime('20100316T141405 '); - - } - - /** - * @depends testParseICalendarDateTime - */ - function testParseICalendarDateTimeUTC() { - - $dateTime = DateTimeParser::parseDateTime('20100316T141405Z'); - - $compare = new DateTime('2010-03-16 14:14:05',new DateTimeZone('UTC')); - $this->assertEquals($compare, $dateTime); - - } - - /** - * @depends testParseICalendarDateTime - */ - function testParseICalendarDateTimeUTC2() { - - $dateTime = DateTimeParser::parseDateTime('20101211T160000Z'); - - $compare = new DateTime('2010-12-11 16:00:00',new DateTimeZone('UTC')); - $this->assertEquals($compare, $dateTime); - - } - - /** - * @depends testParseICalendarDateTime - */ - function testParseICalendarDateTimeCustomTimeZone() { - - $dateTime = DateTimeParser::parseDateTime('20100316T141405', new DateTimeZone('Europe/Amsterdam')); - - $compare = new DateTime('2010-03-16 14:14:05',new DateTimeZone('Europe/Amsterdam')); - $this->assertEquals($compare, $dateTime); - - } - - function testParseICalendarDate() { - - $dateTime = DateTimeParser::parseDate('20100316'); - - $expected = new DateTime('2010-03-16 00:00:00',new DateTimeZone('UTC')); - - $this->assertEquals($expected, $dateTime); - - $dateTime = DateTimeParser::parse('20100316'); - $this->assertEquals($expected, $dateTime); - - } - - /** - * TCheck if a date with year > 4000 will not throw an exception. iOS seems to use 45001231 in yearly recurring events - */ - function testParseICalendarDateGreaterThan4000() { - - $dateTime = DateTimeParser::parseDate('45001231'); - - $expected = new DateTime('4500-12-31 00:00:00',new DateTimeZone('UTC')); - - $this->assertEquals($expected, $dateTime); - - $dateTime = DateTimeParser::parse('45001231'); - $this->assertEquals($expected, $dateTime); - - } - - /** - * Check if a datetime with year > 4000 will not throw an exception. iOS seems to use 45001231T235959 in yearly recurring events - */ - function testParseICalendarDateTimeGreaterThan4000() { - - $dateTime = DateTimeParser::parseDateTime('45001231T235959'); - - $expected = new DateTime('4500-12-31 23:59:59',new DateTimeZone('UTC')); - - $this->assertEquals($expected, $dateTime); - - $dateTime = DateTimeParser::parse('45001231T235959'); - $this->assertEquals($expected, $dateTime); - - } - - /** - * @depends testParseICalendarDate - * @expectedException LogicException - */ - function testParseICalendarDateBadFormat() { - - $dateTime = DateTimeParser::parseDate('20100316T141405'); - - } - - /** - * @dataProvider vcardDates - */ - function testVCardDate($input, $output) { - - $this->assertEquals( - $output, - DateTimeParser::parseVCardDateTime($input) - ); - - } - - /** - * @dataProvider vcardDates - * @expectedException \InvalidArgumentException - */ - function testBadVCardDate() { - - DateTimeParser::parseVCardDateTime('1985---01'); - - } - - /** - * @dataProvider vcardDates - * @expectedException \InvalidArgumentException - */ - function testBadVCardTime() { - - DateTimeParser::parseVCardTime('23:12:166'); - - } - - function vcardDates() { - - return array( - array( - "19961022T140000", - array( - "year" => 1996, - "month" => 10, - "date" => 22, - "hour" => 14, - "minute" => 00, - "second" => 00, - "timezone" => null - ), - ), - array( - "--1022T1400", - array( - "year" => null, - "month" => 10, - "date" => 22, - "hour" => 14, - "minute" => 00, - "second" => null, - "timezone" => null - ), - ), - array( - "---22T14", - array( - "year" => null, - "month" => null, - "date" => 22, - "hour" => 14, - "minute" => null, - "second" => null, - "timezone" => null - ), - ), - array( - "19850412", - array( - "year" => 1985, - "month" => 4, - "date" => 12, - "hour" => null, - "minute" => null, - "second" => null, - "timezone" => null - ), - ), - array( - "1985-04", - array( - "year" => 1985, - "month" => 04, - "date" => null, - "hour" => null, - "minute" => null, - "second" => null, - "timezone" => null - ), - ), - array( - "1985", - array( - "year" => 1985, - "month" => null, - "date" => null, - "hour" => null, - "minute" => null, - "second" => null, - "timezone" => null - ), - ), - array( - "--0412", - array( - "year" => null, - "month" => 4, - "date" => 12, - "hour" => null, - "minute" => null, - "second" => null, - "timezone" => null - ), - ), - array( - "---12", - array( - "year" => null, - "month" => null, - "date" => 12, - "hour" => null, - "minute" => null, - "second" => null, - "timezone" => null - ), - ), - array( - "T102200", - array( - "year" => null, - "month" => null, - "date" => null, - "hour" => 10, - "minute" => 22, - "second" => 0, - "timezone" => null - ), - ), - array( - "T1022", - array( - "year" => null, - "month" => null, - "date" => null, - "hour" => 10, - "minute" => 22, - "second" => null, - "timezone" => null - ), - ), - array( - "T10", - array( - "year" => null, - "month" => null, - "date" => null, - "hour" => 10, - "minute" => null, - "second" => null, - "timezone" => null - ), - ), - array( - "T-2200", - array( - "year" => null, - "month" => null, - "date" => null, - "hour" => null, - "minute" => 22, - "second" => 00, - "timezone" => null - ), - ), - array( - "T--00", - array( - "year" => null, - "month" => null, - "date" => null, - "hour" => null, - "minute" => null, - "second" => 00, - "timezone" => null - ), - ), - array( - "T102200Z", - array( - "year" => null, - "month" => null, - "date" => null, - "hour" => 10, - "minute" => 22, - "second" => 00, - "timezone" => 'Z' - ), - ), - array( - "T102200-0800", - array( - "year" => null, - "month" => null, - "date" => null, - "hour" => 10, - "minute" => 22, - "second" => 00, - "timezone" => '-0800' - ), - ), - - // extended format - array( - "2012-11-29T15:10:53Z", - array( - "year" => 2012, - "month" => 11, - "date" => 29, - "hour" => 15, - "minute" => 10, - "second" => 53, - "timezone" => 'Z' - ), - ), - ); - - } - - -}
--- a/vendor/sabre/vobject/tests/VObject/DocumentTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,70 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class DocumentTest extends \PHPUnit_Framework_TestCase { - - function testGetDocumentType() { - - $doc = new MockDocument(); - $this->assertEquals(Document::UNKNOWN, $doc->getDocumentType()); - - } - - function testConstruct() { - - $doc = new MockDocument('VLIST'); - $this->assertEquals('VLIST', $doc->name); - - } - - function testCreateComponent() { - - $vcal = new Component\VCalendar(array(), false); - - $event = $vcal->createComponent('VEVENT'); - - $this->assertInstanceOf('Sabre\VObject\Component\VEvent', $event); - $vcal->add($event); - - $prop = $vcal->createProperty('X-PROP','1234256',array('X-PARAM' => '3')); - $this->assertInstanceOf('Sabre\VObject\Property', $prop); - - $event->add($prop); - - unset( - $event->DTSTAMP, - $event->UID - ); - - $out = $vcal->serialize(); - $this->assertEquals("BEGIN:VCALENDAR\r\nBEGIN:VEVENT\r\nX-PROP;X-PARAM=3:1234256\r\nEND:VEVENT\r\nEND:VCALENDAR\r\n", $out); - - } - - function testCreate() { - - $vcal = new Component\VCalendar(array(), false); - - $event = $vcal->create('VEVENT'); - $this->assertInstanceOf('Sabre\VObject\Component\VEvent', $event); - - $event = $vcal->create('CALSCALE'); - $this->assertInstanceOf('Sabre\VObject\Property\Text', $event); - - } - - function testGetClassNameForPropertyValue() { - - $vcal = new Component\VCalendar(array(), false); - $this->assertEquals('Sabre\\VObject\\Property\\Text', $vcal->getClassNameForPropertyValue('TEXT')); - $this->assertNull($vcal->getClassNameForPropertyValue('FOO')); - - } - -} - - -class MockDocument extends Document { - -}
--- a/vendor/sabre/vobject/tests/VObject/ElementListTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,33 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class ElementListTest extends \PHPUnit_Framework_TestCase { - - function testIterate() { - - $cal = new Component\VCalendar(); - $sub = $cal->createComponent('VEVENT'); - - $elems = array( - $sub, - clone $sub, - clone $sub - ); - - $elemList = new ElementList($elems); - - $count = 0; - foreach($elemList as $key=>$subcomponent) { - - $count++; - $this->assertInstanceOf('Sabre\\VObject\\Component',$subcomponent); - - } - $this->assertEquals(3,$count); - $this->assertEquals(2,$key); - - } - - -}
--- a/vendor/sabre/vobject/tests/VObject/EmClientTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,55 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class EmClientTest extends \PHPUnit_Framework_TestCase { - - function testParseTz() { - - $str = 'BEGIN:VCALENDAR -X-WR-CALNAME:Blackhawks Schedule 2011-12 -X-APPLE-CALENDAR-COLOR:#E51717 -X-WR-TIMEZONE:America/Chicago -CALSCALE:GREGORIAN -PRODID:-//eM Client/4.0.13961.0 -VERSION:2.0 -BEGIN:VTIMEZONE -TZID:America/Chicago -BEGIN:DAYLIGHT -TZOFFSETFROM:-0600 -RRULE:FREQ=YEARLY;BYDAY=2SU;BYMONTH=3 -DTSTART:20070311T020000 -TZNAME:CDT -TZOFFSETTO:-0500 -END:DAYLIGHT -BEGIN:STANDARD -TZOFFSETFROM:-0500 -RRULE:FREQ=YEARLY;BYDAY=1SU;BYMONTH=11 -DTSTART:20071104T020000 -TZNAME:CST -TZOFFSETTO:-0600 -END:STANDARD -END:VTIMEZONE -BEGIN:VEVENT -CREATED:20110624T181236Z -UID:be3bbfff-96e8-4c66-9908-ab791a62231d -DTEND;TZID="America/Chicago":20111008T223000 -TRANSP:OPAQUE -SUMMARY:Stars @ Blackhawks (Home Opener) -DTSTART;TZID="America/Chicago":20111008T193000 -DTSTAMP:20120330T013232Z -SEQUENCE:2 -X-MICROSOFT-CDO-BUSYSTATUS:BUSY -LAST-MODIFIED:20120330T013237Z -CLASS:PUBLIC -END:VEVENT -END:VCALENDAR'; - - $vObject = Reader::read($str); - $dt = $vObject->VEVENT->DTSTART->getDateTime(); - $this->assertEquals(new \DateTime('2011-10-08 19:30:00', new \DateTimeZone('America/Chicago')), $dt); - - } - -} -
--- a/vendor/sabre/vobject/tests/VObject/EmptyParameterTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,69 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class IssueEmptyParameterTest extends \PHPUnit_Framework_TestCase { - - function testRead() { - - $input = <<<VCF -BEGIN:VCARD -VERSION:2.1 -N:Doe;Jon;;; -FN:Jon Doe -EMAIL;X-INTERN:foo@example.org -UID:foo -END:VCARD -VCF; - - $vcard = Reader::read($input); - - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCard', $vcard); - $vcard = $vcard->convert(\Sabre\VObject\Document::VCARD30); - $vcard = $vcard->serialize(); - - $converted = Reader::read($vcard); - $converted->validate(); - - $this->assertTrue(isset($converted->EMAIL['X-INTERN'])); - - $version = Version::VERSION; - - $expected = <<<VCF -BEGIN:VCARD -VERSION:3.0 -PRODID:-//Sabre//Sabre VObject $version//EN -N:Doe;Jon;;; -FN:Jon Doe -EMAIL;X-INTERN=:foo@example.org -UID:foo -END:VCARD - -VCF; - - $this->assertEquals($expected, str_replace("\r","", $vcard)); - - } - - function testVCard21Parameter() { - - $vcard = new Component\VCard(array(), false); - $vcard->VERSION = '2.1'; - $vcard->PHOTO = 'random_stuff'; - $vcard->PHOTO->add(null,'BASE64'); - $vcard->UID = 'foo-bar'; - - $result = $vcard->serialize(); - $expected = array( - "BEGIN:VCARD", - "VERSION:2.1", - "PHOTO;BASE64:" . base64_encode('random_stuff'), - "UID:foo-bar", - "END:VCARD", - "", - ); - - $this->assertEquals(implode("\r\n", $expected), $result); - - } -}
--- a/vendor/sabre/vobject/tests/VObject/EmptyValueIssueTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,31 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * This test is written for Issue 68: - * - * https://github.com/fruux/sabre-vobject/issues/68 - */ -class EmptyValueIssueTest extends \PHPUnit_Framework_TestCase { - - function testDecodeValue() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -DESCRIPTION:This is a descpription\\nwith a linebreak and a \\; \\, and : -END:VEVENT -END:VCALENDAR -ICS; - - $vobj = Reader::read($input); - - // Before this bug was fixed, getValue() would return nothing. - $this->assertEquals("This is a descpription\nwith a linebreak and a ; , and :", $vobj->VEVENT->DESCRIPTION->getValue()); - - } - -} -
--- a/vendor/sabre/vobject/tests/VObject/FreeBusyGeneratorTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,376 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class FreeBusyGeneratorTest extends \PHPUnit_Framework_TestCase { - - function getInput() { - - $tests = array(); - - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART:20110101T120000Z -DTEND:20110101T130000Z -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - "20110101T120000Z/20110101T130000Z" - ); - - // opaque, shows up - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar2 -TRANSP:OPAQUE -DTSTART:20110101T130000Z -DTEND:20110101T140000Z -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - "20110101T130000Z/20110101T140000Z" - ); - - // transparent, hidden - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar3 -TRANSP:TRANSPARENT -DTSTART:20110101T140000Z -DTEND:20110101T150000Z -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - null, - ); - - // cancelled, hidden - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar4 -STATUS:CANCELLED -DTSTART:20110101T160000Z -DTEND:20110101T170000Z -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - null, - ); - - // tentative, shows up - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar5 -STATUS:TENTATIVE -DTSTART:20110101T180000Z -DTEND:20110101T190000Z -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - '20110101T180000Z/20110101T190000Z', - ); - - // outside of time-range, hidden - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar6 -DTSTART:20110101T090000Z -DTEND:20110101T100000Z -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - null, - ); - - // outside of time-range, hidden - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar7 -DTSTART:20110104T090000Z -DTEND:20110104T100000Z -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - null, - ); - - // using duration, shows up - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar8 -DTSTART:20110101T190000Z -DURATION:PT1H -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - '20110101T190000Z/20110101T200000Z', - ); - - // Day-long event, shows up - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar9 -DTSTART;VALUE=DATE:20110102 -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - '20110102T000000Z/20110103T000000Z', - ); - - - // No duration, does not show up - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar10 -DTSTART:20110101T200000Z -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - null, - ); - - // encoded as object, shows up - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar11 -DTSTART:20110101T210000Z -DURATION:PT1H -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - Reader::read($blob), - '20110101T210000Z/20110101T220000Z', - ); - - // Freebusy. Some parts show up - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VFREEBUSY -FREEBUSY:20110103T010000Z/20110103T020000Z -FREEBUSY;FBTYPE=FREE:20110103T020000Z/20110103T030000Z -FREEBUSY:20110103T030000Z/20110103T040000Z,20110103T040000Z/20110103T050000Z -FREEBUSY:20120101T000000Z/20120101T010000Z -FREEBUSY:20110103T050000Z/PT1H -END:VFREEBUSY -END:VCALENDAR -ICS; - - $tests[] = array( - Reader::read($blob), - array( - '20110103T010000Z/20110103T020000Z', - '20110103T030000Z/20110103T040000Z', - '20110103T040000Z/20110103T050000Z', - '20110103T050000Z/20110103T060000Z', - ) - ); - - - // Yearly recurrence rule, shows up - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar13 -DTSTART:20100101T220000Z -DTEND:20100101T230000Z -RRULE:FREQ=YEARLY -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - Reader::read($blob), - '20110101T220000Z/20110101T230000Z', - ); - - - // Yearly recurrence rule + duration, shows up - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar14 -DTSTART:20100101T230000Z -DURATION:PT1H -RRULE:FREQ=YEARLY -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - Reader::read($blob), - '20110101T230000Z/20110102T000000Z', - ); - - // Floating time, no timezone - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART:20110101T120000 -DTEND:20110101T130000 -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - "20110101T120000Z/20110101T130000Z" - ); - - // Floating time + reference timezone - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART:20110101T120000 -DTEND:20110101T130000 -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - "20110101T170000Z/20110101T180000Z", - new \DateTimeZone('America/Toronto') - ); - - // All-day event - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART;VALUE=DATE:20110101 -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - "20110101T000000Z/20110102T000000Z" - ); - - // All-day event + reference timezone - $blob = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART;VALUE=DATE:20110101 -END:VEVENT -END:VCALENDAR -ICS; - - $tests[] = array( - $blob, - "20110101T050000Z/20110102T050000Z", - new \DateTimeZone('America/Toronto') - ); - return $tests; - - } - - /** - * @dataProvider getInput - */ - function testGenerator($input, $expected, $timeZone = null) { - - $gen = new FreeBusyGenerator( - new \DateTime('20110101T110000Z', new \DateTimeZone('UTC')), - new \DateTime('20110103T110000Z', new \DateTimeZone('UTC')), - $input, - $timeZone - ); - - $result = $gen->getResult(); - - $expected = (array)$expected; - - $freebusy = $result->VFREEBUSY->select('FREEBUSY'); - - foreach($freebusy as $fb) { - - $this->assertContains((string)$fb, $expected, "$fb did not appear in our list of expected freebusy strings. This is concerning!"); - - $k = array_search((string)$fb, $expected); - unset($expected[$k]); - - } - $this->assertTrue( - count($expected) === 0, - 'There were elements in the expected array that were not found in the output: ' . "\n" . print_r($expected,true) . "\n" . $result->serialize() - ); - - } - - function testGeneratorBaseObject() { - - $obj = new Component\VCalendar(); - $obj->METHOD = 'PUBLISH'; - - $gen = new FreeBusyGenerator(); - $gen->setObjects(array()); - $gen->setBaseObject($obj); - - $result = $gen->getResult(); - - $this->assertEquals('PUBLISH', $result->METHOD->getValue()); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testInvalidArg() { - - $gen = new FreeBusyGenerator( - new \DateTime('2012-01-01'), - new \DateTime('2012-12-31'), - new \StdClass() - ); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/GoogleColonEscapingTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,31 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Google produces vcards with a weird escaping of urls. - * - * VObject will provide a workaround for this, so end-user still get expected - * values. - */ -class GoogleColonEscaping extends \PHPUnit_Framework_TestCase { - - function testDecode() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:3.0 -FN:Evert Pot -N:Pot;Evert;;; -EMAIL;TYPE=INTERNET;TYPE=WORK:evert@fruux.com -BDAY:1985-04-07 -item7.URL:http\://www.rooftopsolutions.nl/ -END:VCARD -VCF; - - $vobj = Reader::read($vcard); - $this->assertEquals('http://www.rooftopsolutions.nl/', $vobj->URL->getValue()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/ICalendar/AttachParseTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,31 +0,0 @@ -<?php - -namespace Sabre\VObject\ICalendar; - -use Sabre\VObject\Reader; - -class AttachParseTest extends \PHPUnit_Framework_TestCase { - - /** - * See issue #128 for more info. - */ - function testParseAttach() { - - $vcal = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -ATTACH;FMTTYPE=application/postscript:ftp://example.com/pub/reports/r-960812.ps -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($vcal); - $prop = $vcal->VEVENT->ATTACH; - - $this->assertInstanceOf('Sabre\\VObject\\Property\\URI', $prop); - $this->assertEquals('ftp://example.com/pub/reports/r-960812.ps', $prop->getValue()); - - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/ITip/BrokerAttendeeReplyTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,962 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -class BrokerAttendeeReplyTest extends BrokerTester { - - function testAccepted() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SUMMARY:B-day party -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SUMMARY:B-day party -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => 'One', - 'recipient' => 'mailto:strunk@example.org', - 'recipientName' => 'Strunk', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140716T120000Z -SUMMARY:B-day party -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - - ); - - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - function testRecurringReply() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140724T120000Z -SUMMARY:Daily sprint -RRULE;FREQ=DAILY -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=NEEDS-ACTION;CN=One:mailto:one@example.org -DTSTART:20140724T120000Z -SUMMARY:Daily sprint -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -DTSTART:20140726T120000Z -RECURRENCE-ID:20140726T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -DTSTART:20140724T120000Z -RECURRENCE-ID:20140724T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=TENTATIVE;CN=One:mailto:one@example.org -DTSTART:20140728T120000Z -RECURRENCE-ID:20140728T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -DTSTART:20140729T120000Z -RECURRENCE-ID:20140729T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -DTSTART:20140725T120000Z -RECURRENCE-ID:20140725T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => 'One', - 'recipient' => 'mailto:strunk@example.org', - 'recipientName' => 'Strunk', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140726T120000Z -SUMMARY:Daily sprint -RECURRENCE-ID:20140726T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140724T120000Z -SUMMARY:Daily sprint -RECURRENCE-ID:20140724T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140728T120000Z -SUMMARY:Daily sprint -RECURRENCE-ID:20140728T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=TENTATIVE;CN=One:mailto:one@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140729T120000Z -SUMMARY:Daily sprint -RECURRENCE-ID:20140729T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140725T120000Z -SUMMARY:Daily sprint -RECURRENCE-ID:20140725T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - - ); - - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - function testRecurringAllDay() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART;VALUE=DATE:20140724 -RRULE;FREQ=DAILY -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=NEEDS-ACTION;CN=One:mailto:one@example.org -DTSTART;VALUE=DATE:20140724 -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -DTSTART;VALUE=DATE:20140726 -RECURRENCE-ID;VALUE=DATE:20140726 -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -DTSTART;VALUE=DATE:20140724 -RECURRENCE-ID;VALUE=DATE:20140724 -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=TENTATIVE;CN=One:mailto:one@example.org -DTSTART;VALUE=DATE:20140728 -RECURRENCE-ID;VALUE=DATE:20140728 -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -DTSTART;VALUE=DATE:20140729 -RECURRENCE-ID;VALUE=DATE:20140729 -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -DTSTART;VALUE=DATE:20140725 -RECURRENCE-ID;VALUE=DATE:20140725 -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => 'One', - 'recipient' => 'mailto:strunk@example.org', - 'recipientName' => 'Strunk', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;VALUE=DATE:20140726 -RECURRENCE-ID;VALUE=DATE:20140726 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;VALUE=DATE:20140724 -RECURRENCE-ID;VALUE=DATE:20140724 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;VALUE=DATE:20140728 -RECURRENCE-ID;VALUE=DATE:20140728 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=TENTATIVE;CN=One:mailto:one@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;VALUE=DATE:20140729 -RECURRENCE-ID;VALUE=DATE:20140729 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;VALUE=DATE:20140725 -RECURRENCE-ID;VALUE=DATE:20140725 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - - ); - - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - function testNoChange() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=NEEDS-ACTION;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $expected = array(); - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - function testNoChangeForceSend() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;SCHEDULE-FORCE-SEND=REPLY;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=NEEDS-ACTION;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => 'One', - 'recipient' => 'mailto:strunk@example.org', - 'recipientName' => 'Strunk', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140716T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=NEEDS-ACTION;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - ) - - ); - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - function testNoRelevantAttendee() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $expected = array(); - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - /** - * In this test, an event exists in an attendees calendar. The event - * is recurring, and the attendee deletes 1 instance of the event. - * This instance shows up in EXDATE - * - * This should automatically generate a DECLINED message for that - * specific instance. - */ - function testCreateReplyByException() { - - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140811T200000Z -RRULE:FREQ=WEEKLY -ORGANIZER:mailto:organizer@example.org -ATTENDEE:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140811T200000Z -RRULE:FREQ=WEEKLY -ORGANIZER:mailto:organizer@example.org -ATTENDEE:mailto:one@example.org -EXDATE:20140818T200000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => null, - 'recipient' => 'mailto:organizer@example.org', - 'recipientName' => null, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140818T200000Z -RECURRENCE-ID:20140818T200000Z -ORGANIZER:mailto:organizer@example.org -ATTENDEE;PARTSTAT=DECLINED:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - /** - * This test is identical to the last, but now we're working with - * timezones. - * - * @depends testCreateReplyByException - */ - function testCreateReplyByExceptionTz() { - - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;TZID=America/Toronto:20140811T200000 -RRULE:FREQ=WEEKLY -ORGANIZER:mailto:organizer@example.org -ATTENDEE:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;TZID=America/Toronto:20140811T200000 -RRULE:FREQ=WEEKLY -ORGANIZER:mailto:organizer@example.org -ATTENDEE:mailto:one@example.org -EXDATE;TZID=America/Toronto:20140818T200000 -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => null, - 'recipient' => 'mailto:organizer@example.org', - 'recipientName' => null, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;TZID=America/Toronto:20140818T200000 -RECURRENCE-ID;TZID=America/Toronto:20140818T200000 -ORGANIZER:mailto:organizer@example.org -ATTENDEE;PARTSTAT=DECLINED:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - /** - * @depends testCreateReplyByException - */ - function testCreateReplyByExceptionAllDay() { - - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SUMMARY:Weekly meeting -UID:foobar -SEQUENCE:1 -DTSTART;VALUE=DATE:20140811 -RRULE:FREQ=WEEKLY -ORGANIZER:mailto:organizer@example.org -ATTENDEE:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SUMMARY:Weekly meeting -UID:foobar -SEQUENCE:1 -DTSTART;VALUE=DATE:20140811 -RRULE:FREQ=WEEKLY -ORGANIZER:mailto:organizer@example.org -ATTENDEE:mailto:one@example.org -EXDATE;VALUE=DATE:20140818 -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => null, - 'recipient' => 'mailto:organizer@example.org', - 'recipientName' => null, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;VALUE=DATE:20140818 -SUMMARY:Weekly meeting -RECURRENCE-ID;VALUE=DATE:20140818 -ORGANIZER:mailto:organizer@example.org -ATTENDEE;PARTSTAT=DECLINED:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - function testDeclined() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => 'One', - 'recipient' => 'mailto:strunk@example.org', - 'recipientName' => 'Strunk', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140716T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - - ); - - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - function testDeclinedCancelledEvent() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -STATUS:CANCELLED -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -STATUS:CANCELLED -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array(); - - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - /** - * In this test, a new exception is created by an attendee as well. - * - * Except in this case, there was already an overridden event, and the - * overridden event was marked as cancelled by the attendee. - * - * For any other attendence status, the new status would have been - * declined, but for this, no message should we sent. - */ - function testDontCreateReplyWhenEventWasDeclined() { - - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140811T200000Z -RRULE:FREQ=WEEKLY -ORGANIZER:mailto:organizer@example.org -ATTENDEE:mailto:one@example.org -END:VEVENT -BEGIN:VEVENT -RECURRENCE-ID:20140818T200000Z -UID:foobar -SEQUENCE:1 -DTSTART:20140818T200000Z -RRULE:FREQ=WEEKLY -ORGANIZER:mailto:organizer@example.org -ATTENDEE;PARTSTAT=DECLINED:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140811T200000Z -RRULE:FREQ=WEEKLY -ORGANIZER:mailto:organizer@example.org -ATTENDEE:mailto:one@example.org -EXDATE:20140818T200000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - $expected = array(); - - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - function testScheduleAgentOnOrganizer() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;SCHEDULE-AGENT=CLIENT;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array(); - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - - function testAcceptedAllDay() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART;VALUE=DATE:20140716 -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -DTSTART;VALUE=DATE:20140716 -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => 'One', - 'recipient' => 'mailto:strunk@example.org', - 'recipientName' => 'Strunk', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART;VALUE=DATE:20140716 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=ACCEPTED;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - - ); - - $result = $this->parse($oldMessage, $newMessage, $expected); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/ITip/BrokerDeleteEventTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,193 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -class BrokerDeleteEventTest extends BrokerTester { - - function testOrganizerDelete() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -SUMMARY:foo -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = null; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'CANCEL', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:CANCEL -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -SUMMARY:foo -DTSTART:20140716T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - ), - - array( - 'uid' => 'foobar', - 'method' => 'CANCEL', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:two@example.org', - 'recipientName' => 'Two', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:CANCEL -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -SUMMARY:foo -DTSTART:20140716T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - - $result = $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } - - function testAttendeeDelete() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -SUMMARY:foo -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = null; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REPLY', - 'component' => 'VEVENT', - 'sender' => 'mailto:one@example.org', - 'senderName' => 'One', - 'recipient' => 'mailto:strunk@example.org', - 'recipientName' => 'Strunk', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140716T120000Z -SUMMARY:foo -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;PARTSTAT=DECLINED;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - ), - ); - - $result = $this->parse($oldMessage, $newMessage, $expected, 'mailto:one@example.org'); - - - } - - function testAttendeeDeleteCancelledEvent() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -STATUS:CANCELLED -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = null; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array(); - - $result = $this->parse($oldMessage, $newMessage, $expected, 'mailto:one@example.org'); - - - } - - function testNoCalendar() { - - $this->parse(null, null, array(), 'mailto:one@example.org'); - - } - - function testVTodo() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VTODO -UID:foobar -SEQUENCE:1 -END:VTODO -END:VCALENDAR -ICS; - $this->parse($oldMessage, null, array(), 'mailto:one@example.org'); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/ITip/BrokerNewEventTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,507 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -class BrokerNewEventTest extends \PHPUnit_Framework_TestCase { - - function testNoAttendee() { - - $message = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART:20140811T220000Z -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->parse($message); - - } - - function testVTODO() { - - $message = <<<ICS -BEGIN:VCALENDAR -BEGIN:VTODO -UID:foobar -END:VTODO -END:VCALENDAR -ICS; - - $result = $this->parse($message); - - } - - function testSimpleInvite() { - - $message = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -DTSTART:20140811T220000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=White:mailto:white@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - $expectedMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -DTSTART:20140811T220000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=White;PARTSTAT=NEEDS-ACTION:mailto:white@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:white@example.org', - 'recipientName' => 'White', - 'message' => $expectedMessage, - ), - ); - - $result = $this->parse($message, $expected); - - } - - /** - * @expectedException \Sabre\VObject\ITip\ITipException - */ - function testBrokenEventUIDMisMatch() { - - $message = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=White:mailto:white@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=White:mailto:white@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = array(); - $this->parse($message, array()); - - } - /** - * @expectedException \Sabre\VObject\ITip\ITipException - */ - function testBrokenEventOrganizerMisMatch() { - - $message = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=White:mailto:white@example.org -END:VEVENT -BEGIN:VEVENT -UID:foobar -ORGANIZER:mailto:foo@example.org -ATTENDEE;CN=White:mailto:white@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = array(); - $this->parse($message, array()); - - } - - function testRecurrenceInvite() { - - $message = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -RRULE:FREQ=DAILY -EXDATE:20140717T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -RECURRENCE-ID:20140718T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One;PARTSTAT=NEEDS-ACTION:mailto:one@example.org -ATTENDEE;CN=Two;PARTSTAT=NEEDS-ACTION:mailto:two@example.org -DTSTART:20140716T120000Z -RRULE:FREQ=DAILY -EXDATE:20140717T120000Z,20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:two@example.org', - 'recipientName' => 'Two', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One;PARTSTAT=NEEDS-ACTION:mailto:one@example.org -ATTENDEE;CN=Two;PARTSTAT=NEEDS-ACTION:mailto:two@example.org -DTSTART:20140716T120000Z -RRULE:FREQ=DAILY -EXDATE:20140717T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -RECURRENCE-ID:20140718T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:three@example.org', - 'recipientName' => 'Three', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -RECURRENCE-ID:20140718T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - - $result = $this->parse($message, $expected); - - } - - function testRecurrenceInvite2() { - - // This method tests a nearly identical path, but in this case the - // master event does not have an EXDATE. - $message = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -RRULE:FREQ=DAILY -END:VEVENT -BEGIN:VEVENT -UID:foobar -RECURRENCE-ID:20140718T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One;PARTSTAT=NEEDS-ACTION:mailto:one@example.org -ATTENDEE;CN=Two;PARTSTAT=NEEDS-ACTION:mailto:two@example.org -DTSTART:20140716T120000Z -RRULE:FREQ=DAILY -EXDATE:20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:two@example.org', - 'recipientName' => 'Two', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One;PARTSTAT=NEEDS-ACTION:mailto:one@example.org -ATTENDEE;CN=Two;PARTSTAT=NEEDS-ACTION:mailto:two@example.org -DTSTART:20140716T120000Z -RRULE:FREQ=DAILY -END:VEVENT -BEGIN:VEVENT -UID:foobar -RECURRENCE-ID:20140718T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:three@example.org', - 'recipientName' => 'Three', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -RECURRENCE-ID:20140718T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - - $result = $this->parse($message, $expected); - - } - - function testScheduleAgentClient() { - - $message = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -DTSTART:20140811T220000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=White;SCHEDULE-AGENT=CLIENT:mailto:white@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array(); - $result = $this->parse($message, $expected); - - } - - /** - * @expectedException Sabre\VObject\ITip\ITipException - */ - function testMultipleUID() { - - $message = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -RRULE:FREQ=DAILY -END:VEVENT -BEGIN:VEVENT -UID:foobar2 -RECURRENCE-ID:20140718T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - $result = $this->parse($message, array()); - - } - - /** - * @expectedException Sabre\VObject\ITip\SameOrganizerForAllComponentsException - * - */ - function testChangingOrganizers() { - - $message = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -RRULE:FREQ=DAILY -END:VEVENT -BEGIN:VEVENT -UID:foobar -RECURRENCE-ID:20140718T120000Z -ORGANIZER;CN=Strunk:mailto:ew@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140718T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - $result = $this->parse($message, array()); - - } - function testNoOrganizerHasAttendee() { - - $message = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART:20140811T220000Z -ATTENDEE;CN=Two:mailto:two@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $this->parse($message, array()); - - } - - function parse($message, $expected = array()) { - - $broker = new Broker(); - $result = $broker->parseEvent($message, 'mailto:strunk@example.org'); - - $this->assertEquals(count($expected), count($result)); - - foreach($expected as $index=>$ex) { - - $message = $result[$index]; - - foreach($ex as $key=>$val) { - - if ($key==='message') { - $this->assertEquals( - str_replace("\n", "\r\n", $val), - rtrim($message->message->serialize(), "\r\n") - ); - } else { - $this->assertEquals($val, $message->$key); - } - - } - - } - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/ITip/BrokerProcessMessageTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,168 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -class BrokerProcessMessageTest extends BrokerTester { - - function testRequestNew() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REQUEST -BEGIN:VEVENT -SEQUENCE:1 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -%foo% -BEGIN:VEVENT -SEQUENCE:1 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, null, $expected); - - } - - function testRequestUpdate() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REQUEST -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -%foo% -BEGIN:VEVENT -SEQUENCE:1 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -%foo% -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, $old, $expected); - - } - - function testCancel() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:CANCEL -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -%foo% -BEGIN:VEVENT -SEQUENCE:1 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -%foo% -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -STATUS:CANCELLED -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, $old, $expected); - - } - - function testCancelNoExistingEvent() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:CANCEL -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = null; - $expected = null; - - $result = $this->process($itip, $old, $expected); - - } - - function testUnsupportedComponent() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VTODO -SEQUENCE:2 -UID:foobar -END:VTODO -END:VCALENDAR -ICS; - - $old = null; - $expected = null; - - $result = $this->process($itip, $old, $expected); - - } - - function testUnsupportedMethod() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:PUBLISH -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = null; - $expected = null; - - $result = $this->process($itip, $old, $expected); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/ITip/BrokerProcessReplyTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,425 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -class BrokerProcessReplyTest extends BrokerTester { - - function testReplyNoOriginal() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REPLY -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -ATTENDEE;PARTSTAT=ACCEPTED:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $old = null; - $expected = null; - - $result = $this->process($itip, $old, $expected); - - } - - function testReplyAccept() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REPLY -BEGIN:VEVENT -ATTENDEE;PARTSTAT=ACCEPTED:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -SEQUENCE:2 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -ATTENDEE:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -ATTENDEE;PARTSTAT=ACCEPTED;SCHEDULE-STATUS=2.0:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, $old, $expected); - - } - - function testReplyRequestStatus() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REPLY -BEGIN:VEVENT -UID:foobar -REQUEST-STATUS:2.3;foo-bar! -ATTENDEE;PARTSTAT=ACCEPTED:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -SEQUENCE:2 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ATTENDEE:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ATTENDEE;PARTSTAT=ACCEPTED;SCHEDULE-STATUS=2.3:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, $old, $expected); - - } - - - function testReplyPartyCrasher() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REPLY -BEGIN:VEVENT -ATTENDEE;PARTSTAT=ACCEPTED:mailto:crasher@example.org -ORGANIZER:mailto:bar@example.org -SEQUENCE:2 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -ATTENDEE:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -ATTENDEE:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -ATTENDEE;PARTSTAT=ACCEPTED:mailto:crasher@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, $old, $expected); - - } - - function testReplyNewException() { - - // This is a reply to 1 instance of a recurring event. This should - // automatically create an exception. - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REPLY -BEGIN:VEVENT -ATTENDEE;PARTSTAT=ACCEPTED:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -SEQUENCE:2 -RECURRENCE-ID:20140725T000000Z -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -RRULE:FREQ=DAILY -DTSTART:20140724T000000Z -ATTENDEE:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -RRULE:FREQ=DAILY -DTSTART:20140724T000000Z -ATTENDEE:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -DTSTART:20140725T000000Z -ATTENDEE;PARTSTAT=ACCEPTED:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -RECURRENCE-ID:20140725T000000Z -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, $old, $expected); - - } - - function testReplyNewExceptionTz() { - - // This is a reply to 1 instance of a recurring event. This should - // automatically create an exception. - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REPLY -BEGIN:VEVENT -ATTENDEE;PARTSTAT=ACCEPTED:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -SEQUENCE:2 -RECURRENCE-ID;TZID=America/Toronto:20140725T000000 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -RRULE:FREQ=DAILY -DTSTART;TZID=America/Toronto:20140724T000000 -ATTENDEE:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -RRULE:FREQ=DAILY -DTSTART;TZID=America/Toronto:20140724T000000 -ATTENDEE:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -DTSTART;TZID=America/Toronto:20140725T000000 -ATTENDEE;PARTSTAT=ACCEPTED:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -RECURRENCE-ID;TZID=America/Toronto:20140725T000000 -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, $old, $expected); - - } - - function testReplyPartyCrashCreateExcepton() { - - // IN this test there's a recurring event that has an exception. The - // exception is missing the attendee. - // - // The attendee party crashes the instance, so it should show up in the - // resulting object. - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REPLY -BEGIN:VEVENT -ATTENDEE;PARTSTAT=ACCEPTED;CN=Crasher!:mailto:crasher@example.org -ORGANIZER:mailto:bar@example.org -SEQUENCE:2 -RECURRENCE-ID:20140725T000000Z -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -RRULE:FREQ=DAILY -DTSTART:20140724T000000Z -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -RRULE:FREQ=DAILY -DTSTART:20140724T000000Z -ORGANIZER:mailto:bar@example.org -END:VEVENT -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -DTSTART:20140725T000000Z -ORGANIZER:mailto:bar@example.org -RECURRENCE-ID:20140725T000000Z -ATTENDEE;PARTSTAT=ACCEPTED;CN=Crasher!:mailto:crasher@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, $old, $expected); - - } - - function testReplyNewExceptionNoMasterEvent() { - - /** - * This iTip message would normally create a new exception, but the - * server is not able to create this new instance, because there's no - * master event to clone from. - * - * This test checks if the message is ignored. - */ - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REPLY -BEGIN:VEVENT -ATTENDEE;PARTSTAT=ACCEPTED;CN=Crasher!:mailto:crasher@example.org -ORGANIZER:mailto:bar@example.org -SEQUENCE:2 -RECURRENCE-ID:20140725T000000Z -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -RRULE:FREQ=DAILY -DTSTART:20140724T000000Z -RECURRENCE-ID:20140724T000000Z -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = null; - $result = $this->process($itip, $old, $expected); - - } - - /** - * @depends testReplyAccept - */ - function testReplyAcceptUpdateRSVP() { - - $itip = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -METHOD:REPLY -BEGIN:VEVENT -ATTENDEE;PARTSTAT=ACCEPTED:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -SEQUENCE:2 -UID:foobar -END:VEVENT -END:VCALENDAR -ICS; - - $old = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -ATTENDEE;RSVP=TRUE:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $expected = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SEQUENCE:2 -UID:foobar -ATTENDEE;PARTSTAT=ACCEPTED;SCHEDULE-STATUS=2.0:mailto:foo@example.org -ORGANIZER:mailto:bar@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $result = $this->process($itip, $old, $expected); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/ITip/BrokerTester.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,103 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -use Sabre\VObject\Reader; - -/** - * Utilities for testing the broker - * - * @copyright Copyright (C) 2011-2015 fruux GmbH (https://fruux.com/). - * @author Evert Pot (http://evertpot.com/) - * @license http://sabre.io/license/ Modified BSD License - */ -abstract class BrokerTester extends \PHPUnit_Framework_TestCase { - - function parse($oldMessage, $newMessage, $expected = array(), $currentUser = 'mailto:one@example.org') { - - $broker = new Broker(); - $result = $broker->parseEvent($newMessage, $currentUser, $oldMessage); - - $this->assertEquals(count($expected), count($result)); - - foreach($expected as $index=>$ex) { - - $message = $result[$index]; - - foreach($ex as $key=>$val) { - - if ($key==='message') { - $this->assertEquals( - str_replace("\n", "\r\n", $val), - rtrim($message->message->serialize(), "\r\n") - ); - } else { - $this->assertEquals($val, $message->$key); - } - - } - - } - - } - - function process($input, $existingObject = null, $expected = false) { - - $version = \Sabre\VObject\Version::VERSION; - - $vcal = Reader::read($input); - - foreach($vcal->getComponents() as $mainComponent) { - break; - } - - $message = new Message(); - $message->message = $vcal; - $message->method = isset($vcal->METHOD)?$vcal->METHOD->getValue():null; - $message->component = $mainComponent->name; - $message->uid = $mainComponent->uid->getValue(); - $message->sequence = isset($vcal->VEVENT[0])?(string)$vcal->VEVENT[0]->SEQUENCE:null; - - if ($message->method === 'REPLY') { - - $message->sender = $mainComponent->ATTENDEE->getValue(); - $message->senderName = isset($mainComponent->ATTENDEE['CN'])?$mainComponent->ATTENDEE['CN']->getValue():null; - $message->recipient = $mainComponent->ORGANIZER->getValue(); - $message->recipientName = isset($mainComponent->ORGANIZER['CN'])?$mainComponent->ORGANIZER['CN']:null; - - } - - $broker = new Broker(); - - if (is_string($existingObject)) { - $existingObject = str_replace( - '%foo%', - "VERSION:2.0\nPRODID:-//Sabre//Sabre VObject $version//EN\nCALSCALE:GREGORIAN", - $existingObject - ); - $existingObject = Reader::read($existingObject); - } - - $result = $broker->processMessage($message, $existingObject); - - if (is_string($expected)) { - $expected = str_replace( - '%foo%', - "VERSION:2.0\nPRODID:-//Sabre//Sabre VObject $version//EN\nCALSCALE:GREGORIAN", - $expected - ); - $expected = str_replace("\n", "\r\n", $expected); - - } - if ($result instanceof \Sabre\VObject\Component\VCalendar) { - $result = $result->serialize(); - $result = rtrim($result,"\r\n"); - } - - $this->assertEquals( - $expected, - $result - ); - - } -}
--- a/vendor/sabre/vobject/tests/VObject/ITip/BrokerUpdateEventTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,719 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -class BrokerUpdateTest extends BrokerTester { - - function testInviteChange() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -SUMMARY:foo -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -SUMMARY:foo -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'CANCEL', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'significantChange' => true, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:CANCEL -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -SUMMARY:foo -DTSTART:20140716T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:two@example.org', - 'recipientName' => 'Two', - 'significantChange' => false, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -SUMMARY:foo -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=Two;PARTSTAT=NEEDS-ACTION:mailto:two@example.org -ATTENDEE;CN=Three;PARTSTAT=NEEDS-ACTION:mailto:three@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:three@example.org', - 'recipientName' => 'Three', - 'significantChange' => true, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -SUMMARY:foo -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=Two;PARTSTAT=NEEDS-ACTION:mailto:two@example.org -ATTENDEE;CN=Three;PARTSTAT=NEEDS-ACTION:mailto:three@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - - $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } - - function testInviteChangeFromNonSchedulingToSchedulingObject() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One;PARTSTAT=NEEDS-ACTION:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - - ); - - $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } - - function testInviteChangeFromSchedulingToNonSchedulingObject() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'CANCEL', - 'component' => 'VEVENT', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:CANCEL -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140716T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - - ); - - $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } - - function testNoAttendees() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array(); - $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } - - function testRemoveInstance() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART;TZID=America/Toronto:20140716T120000 -RRULE:FREQ=WEEKLY -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART;TZID=America/Toronto:20140716T120000 -RRULE:FREQ=WEEKLY -EXDATE;TZID=America/Toronto:20140724T120000 -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One;PARTSTAT=NEEDS-ACTION:mailto:one@example.org -DTSTART;TZID=America/Toronto:20140716T120000 -RRULE:FREQ=WEEKLY -EXDATE;TZID=America/Toronto:20140724T120000 -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - - $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } - - /** - * This test is identical to the first test, except this time we change the - * DURATION property. - * - * This should ensure that the message is significant for every attendee, - */ - function testInviteChangeSignificantChange() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -DURATION:PT1H -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -DURATION:PT2H -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -ATTENDEE;CN=Three:mailto:three@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'CANCEL', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'significantChange' => true, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:CANCEL -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -DTSTART:20140716T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:two@example.org', - 'recipientName' => 'Two', - 'significantChange' => true, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -DURATION:PT2H -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=Two;PARTSTAT=NEEDS-ACTION:mailto:two@example.org -ATTENDEE;CN=Three;PARTSTAT=NEEDS-ACTION:mailto:three@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:three@example.org', - 'recipientName' => 'Three', - 'significantChange' => true, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -DURATION:PT2H -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=Two;PARTSTAT=NEEDS-ACTION:mailto:two@example.org -ATTENDEE;CN=Three;PARTSTAT=NEEDS-ACTION:mailto:three@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - - $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } - - function testInviteNoChange() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'significantChange' => false, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=One;PARTSTAT=NEEDS-ACTION:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - - ); - - $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } - - function testInviteNoChangeForceSend() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;SCHEDULE-FORCE-SEND=REQUEST;CN=One:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'REQUEST', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'significantChange' => true, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk;PARTSTAT=ACCEPTED:mailto:strunk@example.org -ATTENDEE;CN=One;PARTSTAT=NEEDS-ACTION:mailto:one@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS - - ), - - ); - - $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } - - function testInviteRemoveAttendees() { - - $oldMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:1 -SUMMARY:foo -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -ATTENDEE;CN=Two:mailto:two@example.org -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - - $newMessage = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -SUMMARY:foo -DTSTART:20140716T120000Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - - $expected = array( - array( - 'uid' => 'foobar', - 'method' => 'CANCEL', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:one@example.org', - 'recipientName' => 'One', - 'significantChange' => true, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:CANCEL -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -SUMMARY:foo -DTSTART:20140716T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=One:mailto:one@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - array( - 'uid' => 'foobar', - 'method' => 'CANCEL', - 'component' => 'VEVENT', - 'sender' => 'mailto:strunk@example.org', - 'senderName' => 'Strunk', - 'recipient' => 'mailto:two@example.org', - 'recipientName' => 'Two', - 'significantChange' => true, - 'message' => <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:CANCEL -BEGIN:VEVENT -UID:foobar -SEQUENCE:2 -SUMMARY:foo -DTSTART:20140716T120000Z -ORGANIZER;CN=Strunk:mailto:strunk@example.org -ATTENDEE;CN=Two:mailto:two@example.org -END:VEVENT -END:VCALENDAR -ICS - - ), - ); - - $result = $this->parse($oldMessage, $newMessage, $expected, 'mailto:strunk@example.org'); - - } -}
--- a/vendor/sabre/vobject/tests/VObject/ITip/EvolutionTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,2653 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -class EvolutionTest extends BrokerTester { - - /** - * Evolution does things as usual a little bit differently. - * - * We're adding a seprate test just for it. - */ - function testNewEvolutionEvent() { - - $ics = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -CALSCALE:GREGORIAN -PRODID:-//Ximian//NONSGML Evolution Calendar//EN -BEGIN:VTIMEZONE -TZID:/freeassociation.sourceforge.net/Tzfile/America/Toronto -X-LIC-LOCATION:America/Toronto -BEGIN:STANDARD -TZNAME:EST -DTSTART:19691026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19700426T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19701025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19710425T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19711031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19720430T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19721029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19730429T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19731028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19740428T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19741027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19750427T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19751026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19760425T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19761031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19770424T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19771030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19780430T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19781029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19790429T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19791028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19800427T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19801026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19810426T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19811025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19820425T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19821031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19830424T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19831030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19840429T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19841028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19850428T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19851027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19860427T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19861026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19870405T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19871025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19880403T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19881030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19890402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19891029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19900401T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19901028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19910407T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19911027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19920405T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19921025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19930404T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19931031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19940403T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19941030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19950402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19951029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19960407T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19961027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19970406T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19971026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19980405T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19981025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19990404T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19991031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20000402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20001029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20010401T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20011028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20020407T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20021027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20030406T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20031026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20040404T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20041031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20050403T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20051030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20060402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20061029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20070311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20071104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20080309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20081102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20090308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20091101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20100314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20101107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20110313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20111106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20120311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20121104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20130310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20131103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20140309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20141102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20150308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20151101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20160313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20161106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20170312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20171105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20180311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20181104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20190310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20191103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20200308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20201101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20210314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20211107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20220313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20221106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20230312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20231105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20240310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20241103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20250309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20251102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20260308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20261101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20270314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20271107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20280312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20281105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20290311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20291104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20300310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20301103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20310309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20311102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20320314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20321107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20330313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20331106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20340312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20341105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20350311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20351104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20360309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20361102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20370308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20371101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -END:VTIMEZONE -BEGIN:VEVENT -UID:20140813T153116Z-12176-1000-1065-6@johnny-lubuntu -DTSTAMP:20140813T142829Z -DTSTART;TZID=/freeassociation.sourceforge.net/Tzfile/America/Toronto:201408 - 15T110000 -DTEND;TZID=/freeassociation.sourceforge.net/Tzfile/America/Toronto:20140815 - T113000 -TRANSP:OPAQUE -SEQUENCE:2 -SUMMARY:Evo makes a Meeting (fruux HQ) (fruux HQ) -LOCATION:fruux HQ -CLASS:PUBLIC -ORGANIZER;SENT-BY="MAILTO:martin+johnny@fruux.com":MAILTO:martin@fruux.com -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=ACCEPTED;RSVP=TRUE - ;SENT-BY="MAILTO:martin+johnny@fruux.com";LANGUAGE=en:MAILTO:martin@fruux. - com -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;RSVP= - TRUE;LANGUAGE=en:MAILTO:dominik@fruux.com -CREATED:20140813T153211Z -LAST-MODIFIED:20140813T155353Z -END:VEVENT -END:VCALENDAR -ICS; - - $version = \Sabre\VObject\Version::VERSION; - $expectedICS = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -METHOD:REQUEST -BEGIN:VTIMEZONE -TZID:/freeassociation.sourceforge.net/Tzfile/America/Toronto -X-LIC-LOCATION:America/Toronto -BEGIN:STANDARD -TZNAME:EST -DTSTART:19691026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19700426T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19701025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19710425T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19711031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19720430T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19721029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19730429T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19731028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19740428T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19741027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19750427T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19751026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19760425T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19761031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19770424T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19771030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19780430T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19781029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19790429T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19791028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19800427T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19801026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19810426T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19811025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19820425T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19821031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19830424T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19831030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19840429T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19841028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19850428T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19851027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19860427T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19861026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19870405T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19871025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19880403T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19881030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19890402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19891029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19900401T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19901028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19910407T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19911027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19920405T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19921025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19930404T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19931031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19940403T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19941030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19950402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19951029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19960407T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19961027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19970406T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19971026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19980405T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19981025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19990404T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19991031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20000402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20001029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20010401T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20011028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20020407T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20021027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20030406T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20031026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20040404T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20041031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20050403T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20051030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20060402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20061029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20070311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20071104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20080309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20081102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20090308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20091101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20100314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20101107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20110313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20111106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20120311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20121104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20130310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20131103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20140309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20141102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20150308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20151101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20160313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20161106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20170312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20171105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20180311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20181104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20190310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20191103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20200308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20201101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20210314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20211107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20220313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20221106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20230312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20231105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20240310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20241103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20250309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20251102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20260308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20261101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20270314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20271107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20280312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20281105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20290311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20291104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20300310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20301103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20310309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20311102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20320314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20321107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20330313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20331106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20340312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20341105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20350311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20351104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20360309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20361102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20370308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20371101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -END:VTIMEZONE -BEGIN:VEVENT -UID:20140813T153116Z-12176-1000-1065-6@johnny-lubuntu -DTSTAMP:20140813T142829Z -DTSTART;TZID=/freeassociation.sourceforge.net/Tzfile/America/Toronto:201408 - 15T110000 -DTEND;TZID=/freeassociation.sourceforge.net/Tzfile/America/Toronto:20140815 - T113000 -TRANSP:OPAQUE -SEQUENCE:2 -SUMMARY:Evo makes a Meeting (fruux HQ) (fruux HQ) -LOCATION:fruux HQ -CLASS:PUBLIC -ORGANIZER;SENT-BY="MAILTO:martin+johnny@fruux.com":MAILTO:martin@fruux.com -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=ACCEPTED;RSVP=TRUE - ;SENT-BY="MAILTO:martin+johnny@fruux.com";LANGUAGE=en:MAILTO:martin@fruux. - com -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;RSVP= - TRUE;LANGUAGE=en:MAILTO:dominik@fruux.com -CREATED:20140813T153211Z -LAST-MODIFIED:20140813T155353Z -END:VEVENT -END:VCALENDAR -ICS; - - $expected = array( - array( - 'uid' => '20140813T153116Z-12176-1000-1065-6@johnny-lubuntu', - 'method' => 'REQUEST', - 'sender' => 'mailto:martin@fruux.com', - 'senderName' => null, - 'recipient' => 'mailto:dominik@fruux.com', - 'recipientName' => null, - 'message' => $expectedICS, - ) - ); - $this->parse(null, $ics, $expected, 'mailto:martin@fruux.com'); - - } - - /** - * This is an event originally from evolution, then parsed by sabredav and - * again mangled by iCal. This triggered a few bugs related to email - * address scheme casing. - */ - public function testAttendeeModify() { - - $old = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject 3.3.1//EN -CALSCALE:GREGORIAN -BEGIN:VTIMEZONE -TZID:/freeassociation.sourceforge.net/Tzfile/America/Toronto -X-LIC-LOCATION:America/Toronto -BEGIN:STANDARD -TZNAME:EST -DTSTART:19691026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19700426T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19701025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19710425T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19711031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19720430T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19721029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19730429T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19731028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19740428T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19741027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19750427T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19751026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19760425T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19761031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19770424T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19771030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19780430T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19781029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19790429T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19791028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19800427T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19801026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19810426T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19811025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19820425T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19821031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19830424T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19831030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19840429T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19841028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19850428T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19851027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19860427T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19861026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19870405T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19871025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19880403T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19881030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19890402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19891029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19900401T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19901028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19910407T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19911027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19920405T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19921025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19930404T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19931031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19940403T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19941030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19950402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19951029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19960407T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19961027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19970406T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19971026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19980405T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19981025T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19990404T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19991031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20000402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20001029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20010401T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20011028T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20020407T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20021027T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20030406T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20031026T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20040404T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20041031T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20050403T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20051030T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20060402T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20061029T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20070311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20071104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20080309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20081102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20090308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20091101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20100314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20101107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20110313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20111106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20120311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20121104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20130310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20131103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20140309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20141102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20150308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20151101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20160313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20161106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20170312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20171105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20180311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20181104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20190310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20191103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20200308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20201101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20210314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20211107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20220313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20221106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20230312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20231105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20240310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20241103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20250309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20251102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20260308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20261101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20270314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20271107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20280312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20281105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20290311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20291104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20300310T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20301103T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20310309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20311102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20320314T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20321107T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20330313T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20331106T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20340312T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20341105T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20350311T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20351104T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20360309T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20361102T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:20370308T020000 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZNAME:EST -DTSTART:20371101T020000 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -END:VTIMEZONE -BEGIN:VEVENT -UID:20140813T212317Z-6646-1000-1221-23@evert-ubuntu -DTSTAMP:20140813T212221Z -DTSTART;TZID=/freeassociation.sourceforge.net/Tzfile/America/Toronto:201408 - 13T180000 -DTEND;TZID=/freeassociation.sourceforge.net/Tzfile/America/Toronto:20140813 - T200000 -TRANSP:OPAQUE -SEQUENCE:4 -SUMMARY:Testing evolution -LOCATION:Online -CLASS:PUBLIC -ORGANIZER:MAILTO:o@example.org -CREATED:20140813T212510Z -LAST-MODIFIED:20140813T212541Z -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=ACCEPTED;RSVP=TRUE;LANGUAGE=en:MAILTO:o@example.org -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;RSVP=TRUE;LANGUAGE=en:MAILTO:a1@example.org -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;RSVP=TRUE;LANGUAGE=en:MAILTO:a2@example.org -ATTENDEE;CUTYPE=INDIVIDUAL;ROLE=REQ-PARTICIPANT;PARTSTAT=NEEDS-ACTION;RSVP=TRUE;LANGUAGE=en:MAILTO:a3@example.org -STATUS:CANCELLED -END:VEVENT -END:VCALENDAR -ICS; - - $new = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Apple Inc.//Mac OS X 10.9.4//EN -CALSCALE:GREGORIAN -BEGIN:VTIMEZONE -TZID:America/Toronto -BEGIN:DAYLIGHT -TZOFFSETFROM:-0500 -RRULE:FREQ=YEARLY;BYMONTH=3;BYDAY=2SU -DTSTART:20070311T020000 -TZNAME:EDT -TZOFFSETTO:-0400 -END:DAYLIGHT -BEGIN:STANDARD -TZOFFSETFROM:-0400 -RRULE:FREQ=YEARLY;BYMONTH=11;BYDAY=1SU -DTSTART:20071104T020000 -TZNAME:EST -TZOFFSETTO:-0500 -END:STANDARD -END:VTIMEZONE -BEGIN:VEVENT -TRANSP:OPAQUE -DTEND;TZID=America/Toronto:20140813T200000 -ORGANIZER:MAILTO:o@example.org -UID:20140813T212317Z-6646-1000-1221-23@evert-ubuntu -DTSTAMP:20140813T212221Z -LOCATION:Online -STATUS:CANCELLED -SEQUENCE:4 -CLASS:PUBLIC -SUMMARY:Testing evolution -LAST-MODIFIED:20140813T212541Z -DTSTART;TZID=America/Toronto:20140813T180000 -CREATED:20140813T212510Z -ATTENDEE;CUTYPE=INDIVIDUAL;LANGUAGE=en;PARTSTAT=NEEDS-ACTION;ROLE=REQ-PARTICIPANT;RSVP=TRUE:MAILTO:a2@example.org -ATTENDEE;CUTYPE=INDIVIDUAL;LANGUAGE=en;PARTSTAT=ACCEPTED;ROLE=REQ-PARTICIPANT;RSVP=TRUE:MAILTO:o@example.org -ATTENDEE;CUTYPE=INDIVIDUAL;LANGUAGE=en;PARTSTAT=NEEDS-ACTION;ROLE=REQ-PARTICIPANT;RSVP=TRUE:MAILTO:a1@example.org -ATTENDEE;CUTYPE=INDIVIDUAL;LANGUAGE=en;PARTSTAT=NEEDS-ACTION;ROLE=REQ-PARTICIPANT;RSVP=TRUE:MAILTO:a3@example.org -END:VEVENT -END:VCALENDAR -ICS; - - $this->parse($old, $new, array(), 'mailto:a1@example.org'); - - - } - - -}
--- a/vendor/sabre/vobject/tests/VObject/ITip/MessageTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,32 +0,0 @@ -<?php - -namespace Sabre\VObject\ITip; - -class MessageTest extends \PHPUnit_Framework_TestCase { - - public function testNoScheduleStatus() { - - $message = new Message(); - $this->assertFalse($message->getScheduleStatus()); - - } - - public function testScheduleStatus() { - - $message = new Message(); - $message->scheduleStatus = '1.2;Delivered'; - - $this->assertEquals('1.2', $message->getScheduleStatus()); - - } - - public function testUnexpectedScheduleStatus() { - - $message = new Message(); - $message->scheduleStatus = '9.9.9'; - - $this->assertEquals('9.9.9', $message->getScheduleStatus()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Issue153Test.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,14 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class Issue153Test extends \PHPUnit_Framework_TestCase { - - function testRead() { - - $obj = Reader::read(file_get_contents(dirname(__FILE__) . '/issue153.vcf')); - $this->assertEquals('Test Benutzer', (string)$obj->fn); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Issue26Test.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,36 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - DateTime, - DateTimeZone; - -class Issue26Test extends \PHPUnit_Framework_TestCase { - - /** - * @expectedException \InvalidArgumentException - */ - function testExpand() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:bae5d57a98 -RRULE:FREQ=MONTHLY;BYDAY=0MO,0TU,0WE,0TH,0FR;INTERVAL=1 -DTSTART;VALUE=DATE:20130401 -DTEND;VALUE=DATE:20130402 -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($input); - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCalendar', $vcal); - - $it = new Recur\EventIterator($vcal, 'bae5d57a98'); - iterator_to_array($it); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Issue36WorkAroundTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,39 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class Issue36WorkAroundTest extends \PHPUnit_Framework_TestCase { - - function testWorkaround() { - - // See https://github.com/fruux/sabre-vobject/issues/36 - $event = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -SUMMARY:Titel -SEQUENCE:1 -TRANSP:TRANSPARENT -RRULE:FREQ=YEARLY -LAST-MODIFIED:20130323T225737Z -DTSTAMP:20130323T225737Z -UID:1833bd44-188b-405c-9f85-1a12105318aa -CATEGORIES:Jubiläum -X-MOZ-GENERATION:3 -RECURRENCE-ID;RANGE=THISANDFUTURE;VALUE=DATE:20131013 -DTSTART;VALUE=DATE:20131013 -CREATED:20100721T121914Z -DURATION:P1D -END:VEVENT -END:VCALENDAR -ICS; - - $obj = Reader::read($event); - - // If this does not throw an exception, it's all good. - $it = new Recur\EventIterator($obj,'1833bd44-188b-405c-9f85-1a12105318aa'); - $this->assertInstanceOf('Sabre\\VObject\\Recur\EventIterator', $it); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Issue40Test.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,30 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * This test is created to handle the issues brought forward by issue 40. - * - * https://github.com/fruux/sabre-vobject/issues/40 - */ -class Issue40Test extends \PHPUnit_Framework_TestCase { - - function testEncode() { - - $card = new Component\VCard(); - $card->add('N', array('van der Harten', array('Rene','J.'), "", 'Sir','R.D.O.N.'), array('SORT-AS' => array('Harten','Rene'))); - - $expected = implode("\r\n", array( - "BEGIN:VCARD", - "VERSION:3.0", - "PRODID:-//Sabre//Sabre VObject " . Version::VERSION . '//EN', - "N;SORT-AS=Harten,Rene:van der Harten;Rene,J.;;Sir;R.D.O.N.", - "END:VCARD", - "" - )); - - $this->assertEquals($expected, $card->serialize()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Issue64Test.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,19 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class Issue64Test extends \PHPUnit_Framework_TestCase { - - function testRead() { - - $vcard = Reader::read(file_get_contents(dirname(__FILE__) . '/issue64.vcf')); - $vcard = $vcard->convert(\Sabre\VObject\Document::VCARD30); - $vcard = $vcard->serialize(); - - $converted = Reader::read($vcard); - - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCard', $converted); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Issue96Test.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,24 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class Issue96Test extends \PHPUnit_Framework_TestCase { - - function testRead() { - - $input = <<<VCF -BEGIN:VCARD -VERSION:2.1 -SOURCE:Yahoo Contacts (http://contacts.yahoo.com) -URL;CHARSET=utf-8;ENCODING=QUOTED-PRINTABLE:= -http://www.example.org -END:VCARD -VCF; - - $vcard = Reader::read($input, Reader::OPTION_FORGIVING); - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCard', $vcard); - $this->assertEquals("http://www.example.org", $vcard->url->getValue()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/JCalTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,150 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class JCalTest extends \PHPUnit_Framework_TestCase { - - function testToJCal() { - - $cal = new Component\VCalendar(); - - $event = $cal->add('VEVENT', array( - "UID" => "foo", - "DTSTART" => new \DateTime("2013-05-26 18:10:00Z"), - "DURATION" => "P1D", - "CATEGORIES" => array('home', 'testing'), - "CREATED" => new \DateTime("2013-05-26 18:10:00Z"), - - "ATTENDEE" => "mailto:armin@example.org", - "GEO" => array(51.96668, 7.61876), - "SEQUENCE" => 5, - "FREEBUSY" => array("20130526T210213Z/PT1H", "20130626T120000Z/20130626T130000Z"), - "URL" => "http://example.org/", - "TZOFFSETFROM" => "+05:00", - "RRULE" => array('FREQ' => 'WEEKLY', 'BYDAY' => array('MO','TU')), - )); - - // Modifying DTSTART to be a date-only. - $event->dtstart['VALUE'] = 'DATE'; - $event->add("X-BOOL", true, array('VALUE' => 'BOOLEAN')); - $event->add("X-TIME", "08:00:00", array('VALUE' => 'TIME')); - $event->add("ATTACH", "attachment", array('VALUE' => 'BINARY')); - $event->add("ATTENDEE", "mailto:dominik@example.org", array("CN" => "Dominik", "PARTSTAT" => "DECLINED")); - - $event->add('REQUEST-STATUS', array("2.0", "Success")); - $event->add('REQUEST-STATUS', array("3.7", "Invalid Calendar User", "ATTENDEE:mailto:jsmith@example.org")); - - $event->add('DTEND', '20150108T133000'); - - $expected = array( - "vcalendar", - array( - array( - "version", - new \StdClass(), - "text", - "2.0" - ), - array( - "prodid", - new \StdClass(), - "text", - "-//Sabre//Sabre VObject " . Version::VERSION . "//EN", - ), - array( - "calscale", - new \StdClass(), - "text", - "GREGORIAN" - ), - ), - array( - array("vevent", - array( - array( - "uid", new \StdClass(), "text", "foo", - ), - array( - "dtstart", new \StdClass(), "date", "2013-05-26", - ), - array( - "duration", new \StdClass(), "duration", "P1D", - ), - array( - "categories", new \StdClass(), "text", "home", "testing", - ), - array( - "created", new \StdClass(), "date-time", "2013-05-26T18:10:00Z", - ), - - array( - "attendee", new \StdClass(), "cal-address", "mailto:armin@example.org", - ), - array( - "geo", new \StdClass(), "float", array(51.96668, 7.61876), - ), - array( - "sequence", new \StdClass(), "integer", 5 - ), - array( - "freebusy", new \StdClass(), "period", array("2013-05-26T21:02:13", "PT1H"), array("2013-06-26T12:00:00", "2013-06-26T13:00:00"), - ), - array( - "url", new \StdClass(), "uri", "http://example.org/", - ), - array( - "tzoffsetfrom", new \StdClass(), "utc-offset", "+05:00", - ), - array( - "rrule", new \StdClass(), "recur", array( - 'freq' => 'WEEKLY', - 'byday' => array('MO', 'TU'), - ), - ), - array( - "x-bool", new \StdClass(), "boolean", true - ), - array( - "x-time", new \StdClass(), "time", "08:00:00", - ), - array( - "attach", new \StdClass(), "binary", base64_encode('attachment') - ), - array( - "attendee", - (object)array( - "cn" => "Dominik", - "partstat" => "DECLINED", - ), - "cal-address", - "mailto:dominik@example.org" - ), - array( - "request-status", - new \StdClass(), - "text", - array("2.0", "Success"), - ), - array( - "request-status", - new \StdClass(), - "text", - array("3.7", "Invalid Calendar User", "ATTENDEE:mailto:jsmith@example.org"), - ), - array( - 'dtend', - new \StdClass(), - "date-time", - "2015-01-08T13:30:00", - ), - ), - array(), - ) - ), - ); - - $this->assertEquals($expected, $cal->jsonSerialize()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/JCardTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,195 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class JCardTest extends \PHPUnit_Framework_TestCase { - - function testToJCard() { - - $card = new Component\VCard(array( - "VERSION" => "4.0", - "UID" => "foo", - "BDAY" => "19850407", - "REV" => "19951031T222710Z", - "LANG" => "nl", - "N" => array("Last", "First", "Middle", "", ""), - "item1.TEL" => "+1 555 123456", - "item1.X-AB-LABEL" => "Walkie Talkie", - "ADR" => array( - "", - "", - array("My Street", "Left Side", "Second Shack"), - "Hometown", - "PA", - "18252", - "U.S.A", - ), - )); - - $card->add('BDAY', '1979-12-25', array('VALUE' => 'DATE', 'X-PARAM' => array(1,2))); - $card->add('BDAY', '1979-12-25T02:00:00', array('VALUE' => 'DATE-TIME')); - - - $card->add('X-TRUNCATED', '--1225', array('VALUE' => 'DATE')); - $card->add('X-TIME-LOCAL', '123000', array('VALUE' => 'TIME')); - $card->add('X-TIME-UTC', '12:30:00Z', array('VALUE' => 'TIME')); - $card->add('X-TIME-OFFSET', '12:30:00-08:00', array('VALUE' => 'TIME')); - $card->add('X-TIME-REDUCED', '23', array('VALUE' => 'TIME')); - $card->add('X-TIME-TRUNCATED', '--30', array('VALUE' => 'TIME')); - - $card->add('X-KARMA-POINTS', '42', array('VALUE' => 'INTEGER')); - $card->add('X-GRADE', '1.3', array('VALUE' => 'FLOAT')); - - $card->add('TZ', '-05:00', array('VALUE' => 'UTC-OFFSET')); - - $expected = array( - "vcard", - array( - array( - "version", - new \StdClass(), - "text", - "4.0" - ), - array( - "prodid", - new \StdClass(), - "text", - "-//Sabre//Sabre VObject " . Version::VERSION . "//EN", - ), - array( - "uid", - new \StdClass(), - "text", - "foo", - ), - array( - "bday", - new \StdClass(), - "date-and-or-time", - "1985-04-07", - ), - array( - "rev", - new \StdClass(), - "timestamp", - "1995-10-31T22:27:10Z", - ), - array( - "lang", - new \StdClass(), - "language-tag", - "nl", - ), - array( - "n", - new \StdClass(), - "text", - array("Last", "First", "Middle", "", ""), - ), - array( - "tel", - (object)array( - "group" => "item1", - ), - "text", - "+1 555 123456", - ), - array( - "x-ab-label", - (object)array( - "group" => "item1", - ), - "unknown", - "Walkie Talkie", - ), - array( - "adr", - new \StdClass(), - "text", - array( - "", - "", - array("My Street", "Left Side", "Second Shack"), - "Hometown", - "PA", - "18252", - "U.S.A", - ), - ), - array( - "bday", - (object)array( - 'x-param' => array(1,2), - ), - "date", - "1979-12-25", - ), - array( - "bday", - new \StdClass(), - "date-time", - "1979-12-25T02:00:00", - ), - array( - "x-truncated", - new \StdClass(), - "date", - "--12-25", - ), - array( - "x-time-local", - new \StdClass(), - "time", - "12:30:00" - ), - array( - "x-time-utc", - new \StdClass(), - "time", - "12:30:00Z" - ), - array( - "x-time-offset", - new \StdClass(), - "time", - "12:30:00-08:00" - ), - array( - "x-time-reduced", - new \StdClass(), - "time", - "23" - ), - array( - "x-time-truncated", - new \StdClass(), - "time", - "--30" - ), - array( - "x-karma-points", - new \StdClass(), - "integer", - 42 - ), - array( - "x-grade", - new \StdClass(), - "float", - 1.3 - ), - array( - "tz", - new \StdClass(), - "utc-offset", - "-05:00", - ), - ), - ); - - $this->assertEquals($expected, $card->jsonSerialize()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/LineFoldingIssueTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,23 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class LineFoldingIssueTest extends \PHPUnit_Framework_TestCase { - - function testRead() { - - $event = <<<ICS -BEGIN:VCALENDAR\r -BEGIN:VEVENT\r -DESCRIPTION:TEST\\n\\n \\n\\nTEST\\n\\n \\n\\nTEST\\n\\n \\n\\nTEST\\n\\nTEST\\nTEST, TEST\r -END:VEVENT\r -END:VCALENDAR\r - -ICS; - - $obj = Reader::read($event); - $this->assertEquals($event, $obj->serialize()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/ParameterTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,135 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class ParameterTest extends \PHPUnit_Framework_TestCase { - - function testSetup() { - - $cal = new Component\VCalendar(); - - $param = new Parameter($cal, 'name','value'); - $this->assertEquals('NAME',$param->name); - $this->assertEquals('value',$param->getValue()); - - } - - function testSetupNameLess() { - - $card = new Component\VCard(); - - $param = new Parameter($card, null,'URL'); - $this->assertEquals('VALUE',$param->name); - $this->assertEquals('URL',$param->getValue()); - $this->assertTrue($param->noName); - - } - - function testModify() { - - $cal = new Component\VCalendar(); - - $param = new Parameter($cal, 'name', null); - $param->addValue(1); - $this->assertEquals(array(1), $param->getParts()); - - $param->setParts(array(1,2)); - $this->assertEquals(array(1,2), $param->getParts()); - - $param->addValue(3); - $this->assertEquals(array(1,2,3), $param->getParts()); - - $param->setValue(4); - $param->addValue(5); - $this->assertEquals(array(4,5), $param->getParts()); - - } - - function testCastToString() { - - $cal = new Component\VCalendar(); - $param = new Parameter($cal, 'name', 'value'); - $this->assertEquals('value',$param->__toString()); - $this->assertEquals('value',(string)$param); - - } - - function testCastNullToString() { - - $cal = new Component\VCalendar(); - $param = new Parameter($cal, 'name', null); - $this->assertEquals('',$param->__toString()); - $this->assertEquals('',(string)$param); - - } - - function testSerialize() { - - $cal = new Component\VCalendar(); - $param = new Parameter($cal, 'name', 'value'); - $this->assertEquals('NAME=value',$param->serialize()); - - } - - function testSerializeEmpty() { - - $cal = new Component\VCalendar(); - $param = new Parameter($cal, 'name', null); - $this->assertEquals('NAME=',$param->serialize()); - - } - - function testSerializeComplex() { - - $cal = new Component\VCalendar(); - $param = new Parameter($cal, 'name',array("val1", "val2;", "val3^", "val4\n", "val5\"")); - $this->assertEquals('NAME=val1,"val2;","val3^^","val4^n","val5^\'"',$param->serialize()); - - } - - /** - * iCal 7.0 (OSX 10.9) has major issues with the EMAIL property, when the - * value contains a plus sign, and it's not quoted. - * - * So we specifically added support for that. - */ - function testSerializePlusSign() { - - $cal = new Component\VCalendar(); - $param = new Parameter($cal, 'EMAIL',"user+something@example.org"); - $this->assertEquals('EMAIL="user+something@example.org"',$param->serialize()); - - } - - function testIterate() { - - $cal = new Component\VCalendar(); - - $param = new Parameter($cal, 'name', array(1,2,3,4)); - $result = array(); - - foreach($param as $value) { - $result[] = $value; - } - - $this->assertEquals(array(1,2,3,4), $result); - - } - - function testSerializeColon() { - - $cal = new Component\VCalendar(); - $param = new Parameter($cal, 'name','va:lue'); - $this->assertEquals('NAME="va:lue"',$param->serialize()); - - } - - function testSerializeSemiColon() { - - $cal = new Component\VCalendar(); - $param = new Parameter($cal, 'name','va;lue'); - $this->assertEquals('NAME="va;lue"',$param->serialize()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Parser/JsonTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,395 +0,0 @@ -<?php - -namespace Sabre\VObject\Parser; - -use - Sabre\VObject; - -class JsonTest extends \PHPUnit_Framework_TestCase { - - function testRoundTripJCard() { - - $input = array( - "vcard", - array( - array( - "version", - new \StdClass(), - "text", - "4.0" - ), - array( - "prodid", - new \StdClass(), - "text", - "-//Sabre//Sabre VObject " . VObject\Version::VERSION . "//EN", - ), - array( - "uid", - new \StdClass(), - "text", - "foo", - ), - array( - "bday", - new \StdClass(), - "date-and-or-time", - "1985-04-07", - ), - array( - "rev", - new \StdClass(), - "timestamp", - "1995-10-31T22:27:10Z", - ), - array( - "lang", - new \StdClass(), - "language-tag", - "nl", - ), - array( - "n", - new \StdClass(), - "text", - array("Last", "First", "Middle", "", ""), - ), - array( - "tel", - (object)array( - "group" => "item1", - ), - "text", - "+1 555 123456", - ), - array( - "x-ab-label", - (object)array( - "group" => "item1", - ), - "unknown", - "Walkie Talkie", - ), - array( - "adr", - new \StdClass(), - "text", - array( - "", - "", - array("My Street", "Left Side", "Second Shack"), - "Hometown", - "PA", - "18252", - "U.S.A", - ), - ), - array( - "bday", - (object)array( - 'x-param' => array(1,2), - ), - "date", - "1979-12-25", - ), - array( - "bday", - new \StdClass(), - "date-time", - "1979-12-25T02:00:00", - ), - array( - "x-truncated", - new \StdClass(), - "date", - "--12-25", - ), - array( - "x-time-local", - new \StdClass(), - "time", - "12:30:00" - ), - array( - "x-time-utc", - new \StdClass(), - "time", - "12:30:00Z" - ), - array( - "x-time-offset", - new \StdClass(), - "time", - "12:30:00-08:00" - ), - array( - "x-time-reduced", - new \StdClass(), - "time", - "23" - ), - array( - "x-time-truncated", - new \StdClass(), - "time", - "--30" - ), - array( - "x-karma-points", - new \StdClass(), - "integer", - 42 - ), - array( - "x-grade", - new \StdClass(), - "float", - 1.3 - ), - array( - "tz", - new \StdClass(), - "utc-offset", - "-05:00", - ), - ), - ); - - $parser = new Json(json_encode($input)); - $vobj = $parser->parse(); - - $version = VObject\Version::VERSION; - - - $result = $vobj->serialize(); - $expected = <<<VCF -BEGIN:VCARD -VERSION:4.0 -PRODID:-//Sabre//Sabre VObject $version//EN -UID:foo -BDAY:1985-04-07 -REV:1995-10-31T22:27:10Z -LANG:nl -N:Last;First;Middle;; -item1.TEL:+1 555 123456 -item1.X-AB-LABEL:Walkie Talkie -ADR:;;My Street,Left Side,Second Shack;Hometown;PA;18252;U.S.A -BDAY;X-PARAM=1,2;VALUE=DATE:1979-12-25 -BDAY;VALUE=DATE-TIME:1979-12-25T02:00:00 -X-TRUNCATED;VALUE=DATE:--12-25 -X-TIME-LOCAL;VALUE=TIME:12:30:00 -X-TIME-UTC;VALUE=TIME:12:30:00Z -X-TIME-OFFSET;VALUE=TIME:12:30:00-08:00 -X-TIME-REDUCED;VALUE=TIME:23 -X-TIME-TRUNCATED;VALUE=TIME:--30 -X-KARMA-POINTS;VALUE=INTEGER:42 -X-GRADE;VALUE=FLOAT:1.3 -TZ;VALUE=UTC-OFFSET:-05:00 -END:VCARD - -VCF; - $this->assertEquals($expected, str_replace("\r", "", $result)); - - $this->assertEquals( - $input, - $vobj->jsonSerialize() - ); - - } - - function testRoundTripJCal() { - - $input = array( - "vcalendar", - array( - array( - "version", - new \StdClass(), - "text", - "2.0" - ), - array( - "prodid", - new \StdClass(), - "text", - "-//Sabre//Sabre VObject " . VObject\Version::VERSION . "//EN", - ), - array( - "calscale", - new \StdClass(), - "text", - "GREGORIAN" - ), - ), - array( - array("vevent", - array( - array( - "uid", new \StdClass(), "text", "foo", - ), - array( - "dtstart", new \StdClass(), "date", "2013-05-26", - ), - array( - "duration", new \StdClass(), "duration", "P1D", - ), - array( - "categories", new \StdClass(), "text", "home", "testing", - ), - array( - "created", new \StdClass(), "date-time", "2013-05-26T18:10:00Z", - ), - array( - "attach", new \StdClass(), "binary", base64_encode('attachment') - ), - array( - "attendee", new \StdClass(), "cal-address", "mailto:armin@example.org", - ), - array( - "geo", new \StdClass(), "float", array(51.96668, 7.61876), - ), - array( - "sequence", new \StdClass(), "integer", 5 - ), - array( - "freebusy", new \StdClass(), "period", array("2013-05-26T21:02:13", "PT1H"), array("2013-06-26T12:00:00", "2013-06-26T13:00:00"), - ), - array( - "url", new \StdClass(), "uri", "http://example.org/", - ), - array( - "tzoffsetfrom", new \StdClass(), "utc-offset", "+05:00", - ), - array( - "rrule", new \StdClass(), "recur", array( - 'freq' => 'WEEKLY', - 'byday' => array('MO', 'TU'), - ), - ), - array( - "x-bool", new \StdClass(), "boolean", true - ), - array( - "x-time", new \StdClass(), "time", "08:00:00", - ), - array( - "attendee", - (object)array( - "cn" => "Dominik", - "partstat" => "DECLINED", - ), - "cal-address", - "mailto:dominik@example.org" - ), - array( - "request-status", - new \StdClass(), - "text", - array("2.0", "Success"), - ), - array( - "request-status", - new \StdClass(), - "text", - array("3.7", "Invalid Calendar User", "ATTENDEE:mailto:jsmith@example.org"), - ), - ), - array( - array("valarm", - array( - array( - "action", new \StdClass(), "text", "DISPLAY", - ), - ), - array(), - ), - ), - ) - ), - ); - - $parser = new Json(json_encode($input)); - $vobj = $parser->parse(); - $result = $vobj->serialize(); - - $version = VObject\Version::VERSION; - - $expected = <<<VCF -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $version//EN -CALSCALE:GREGORIAN -BEGIN:VEVENT -UID:foo -DTSTART;VALUE=DATE:20130526 -DURATION:P1D -CATEGORIES:home,testing -CREATED:20130526T181000Z -ATTACH;VALUE=BINARY:YXR0YWNobWVudA== -ATTENDEE:mailto:armin@example.org -GEO:51.96668;7.61876 -SEQUENCE:5 -FREEBUSY:20130526T210213/PT1H,20130626T120000/20130626T130000 -URL:http://example.org/ -TZOFFSETFROM:+05:00 -RRULE:FREQ=WEEKLY;BYDAY=MO,TU -X-BOOL;VALUE=BOOLEAN:TRUE -X-TIME;VALUE=TIME:08:00:00 -ATTENDEE;CN=Dominik;PARTSTAT=DECLINED:mailto:dominik@example.org -REQUEST-STATUS:2.0;Success -REQUEST-STATUS:3.7;Invalid Calendar User;ATTENDEE:mailto:jsmith@example.org -BEGIN:VALARM -ACTION:DISPLAY -END:VALARM -END:VEVENT -END:VCALENDAR - -VCF; - $this->assertEquals($expected, str_replace("\r", "", $result)); - - $this->assertEquals( - $input, - $vobj->jsonSerialize() - ); - - } - - function testParseStreamArg() { - - $input = array( - "vcard", - array( - array( - "FN", new \StdClass(), 'text', "foo", - ), - ), - ); - - $stream = fopen('php://memory','r+'); - fwrite($stream, json_encode($input)); - rewind($stream); - - $result = VObject\Reader::readJson($stream,0); - $this->assertEquals('foo', $result->FN->getValue()); - - } - - /** - * @expectedException \Sabre\VObject\ParseException - */ - function testParseInvalidData() { - - $json = new Json(); - $input = array( - "vlist", - array( - array( - "FN", new \StdClass(), 'text', "foo", - ), - ), - ); - - $json->parse(json_encode($input), 0); - - } -}
--- a/vendor/sabre/vobject/tests/VObject/Parser/MimeDirTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,21 +0,0 @@ -<?php - -namespace Sabre\VObject\Parser; - -/** - * Note that most MimeDir related tests can actually be found in the ReaderTest - * class one level up. - */ -class MimeDirTest extends \PHPUnit_Framework_TestCase { - - /** - * @expectedException \Sabre\VObject\ParseException - */ - function testParseError() { - - $mimeDir = new MimeDir(); - $mimeDir->parse(fopen(__FILE__,'a')); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Parser/QuotedPrintableTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,108 +0,0 @@ -<?php - -namespace Sabre\VObject\Parser; - -use - Sabre\VObject\Reader; - -class QuotedPrintableTest extends \PHPUnit_Framework_TestCase { - - function testReadQuotedPrintableSimple() { - - $data = "BEGIN:VCARD\r\nLABEL;ENCODING=QUOTED-PRINTABLE:Aach=65n\r\nEND:VCARD"; - - $result = Reader::read($data); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCARD', $result->name); - $this->assertEquals(1, count($result->children())); - $this->assertEquals("Aachen", $this->getPropertyValue($result->label)); - - } - - function testReadQuotedPrintableNewlineSoft() { - - $data = "BEGIN:VCARD\r\nLABEL;ENCODING=QUOTED-PRINTABLE:Aa=\r\n ch=\r\n en\r\nEND:VCARD"; - $result = Reader::read($data); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCARD', $result->name); - $this->assertEquals(1, count($result->children())); - $this->assertEquals("Aachen", $this->getPropertyValue($result->label)); - - } - - function testReadQuotedPrintableNewlineHard() { - - $data = "BEGIN:VCARD\r\nLABEL;ENCODING=QUOTED-PRINTABLE:Aachen=0D=0A=\r\n Germany\r\nEND:VCARD"; - $result = Reader::read($data); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCARD', $result->name); - $this->assertEquals(1, count($result->children())); - $this->assertEquals("Aachen\r\nGermany", $this->getPropertyValue($result->label)); - - - } - - function testReadQuotedPrintableCompatibilityMS() { - - $data = "BEGIN:VCARD\r\nLABEL;ENCODING=QUOTED-PRINTABLE:Aachen=0D=0A=\r\nDeutschland:okay\r\nEND:VCARD"; - $result = Reader::read($data, Reader::OPTION_FORGIVING); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCARD', $result->name); - $this->assertEquals(1, count($result->children())); - $this->assertEquals("Aachen\r\nDeutschland:okay", $this->getPropertyValue($result->label)); - - } - - function testReadQuotesPrintableCompoundValues() { - - $data = <<<VCF -BEGIN:VCARD -VERSION:2.1 -N:Doe;John;;; -FN:John Doe -ADR;WORK;CHARSET=UTF-8;ENCODING=QUOTED-PRINTABLE:;;M=C3=BCnster = -Str. 1;M=C3=BCnster;;48143;Deutschland -END:VCARD -VCF; - - $result = Reader::read($data, Reader::OPTION_FORGIVING); - $this->assertEquals(array( - '','','Münster Str. 1','Münster','','48143','Deutschland' - ), $result->ADR->getParts()); - - - } - - private function getPropertyValue(\Sabre\VObject\Property $property) { - - return (string)$property; - - /* - $param = $property['encoding']; - if ($param !== null) { - $encoding = strtoupper((string)$param); - if ($encoding === 'QUOTED-PRINTABLE') { - $value = quoted_printable_decode($value); - } else { - throw new Exception(); - } - } - - $param = $property['charset']; - if ($param !== null) { - $charset = strtoupper((string)$param); - if ($charset !== 'UTF-8') { - $value = mb_convert_encoding($value, 'UTF-8', $charset); - } - } else { - $value = StringUtil::convertToUTF8($value); - } - - return $value; - */ - } -}
--- a/vendor/sabre/vobject/tests/VObject/Property/BinaryTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,19 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject; - -class BinaryTest extends \PHPUnit_Framework_TestCase { - - /** - * @expectedException \InvalidArgumentException - */ - function testMimeDir() { - - $vcard = new VObject\Component\VCard(); - $vcard->add('PHOTO', array('a','b')); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Property/BooleanTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,22 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject; - -class BooleanTest extends \PHPUnit_Framework_TestCase { - - function testMimeDir() { - - $input = "BEGIN:VCARD\r\nX-AWESOME;VALUE=BOOLEAN:TRUE\r\nX-SUCKS;VALUE=BOOLEAN:FALSE\r\nEND:VCARD\r\n"; - - $vcard = VObject\Reader::read($input); - $this->assertTrue($vcard->{'X-AWESOME'}->getValue()); - $this->assertFalse($vcard->{'X-SUCKS'}->getValue()); - - $this->assertEquals('BOOLEAN', $vcard->{'X-AWESOME'}->getValueType()); - $this->assertEquals($input, $vcard->serialize()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Property/CompoundTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,50 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject\Component\VCard; - -class CompoundTest extends \PHPUnit_Framework_TestCase { - - function testSetParts() { - - $arr = array( - 'ABC, Inc.', - 'North American Division', - 'Marketing;Sales', - ); - - $vcard = new VCard(); - $elem = $vcard->createProperty('ORG'); - $elem->setParts($arr); - - $this->assertEquals('ABC\, Inc.;North American Division;Marketing\;Sales', $elem->getValue()); - $this->assertEquals(3, count($elem->getParts())); - $parts = $elem->getParts(); - $this->assertEquals('Marketing;Sales', $parts[2]); - - } - - function testGetParts() { - - $str = 'ABC\, Inc.;North American Division;Marketing\;Sales'; - - $vcard = new VCard(); - $elem = $vcard->createProperty('ORG'); - $elem->setRawMimeDirValue($str); - - $this->assertEquals(3, count($elem->getParts())); - $parts = $elem->getParts(); - $this->assertEquals('Marketing;Sales', $parts[2]); - } - - function testGetPartsNull() { - - $vcard = new VCard(); - $elem = $vcard->createProperty('ORG', null); - - $this->assertEquals(0, count($elem->getParts())); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Property/FloatTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,30 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject; - -class FloatTest extends \PHPUnit_Framework_TestCase { - - function testMimeDir() { - - $input = "BEGIN:VCARD\r\nVERSION:4.0\r\nX-FLOAT;VALUE=FLOAT:0.234;1.245\r\nEND:VCARD\r\n"; - $mimeDir = new VObject\Parser\MimeDir($input); - - $result = $mimeDir->parse($input); - - $this->assertInstanceOf('Sabre\VObject\Property\Float', $result->{'X-FLOAT'}); - - $this->assertEquals(array( - 0.234, - 1.245, - ), $result->{'X-FLOAT'}->getParts()); - - $this->assertEquals( - $input, - $result->serialize() - ); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Property/ICalendar/CalAddressTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,32 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -class CalAddressTest extends \PHPUnit_Framework_TestCase { - - /** - * @dataProvider values - */ - function testGetNormalizedValue($expected, $input) { - - $vobj = new \Sabre\VObject\Component\VCalendar(); - $property = $vobj->add('ATTENDEE', $input); - - $this->assertEquals( - $expected, - $property->getNormalizedValue() - ); - - } - - function values() { - - return array( - array('mailto:a@b.com', 'mailto:a@b.com'), - array('mailto:a@b.com', 'MAILTO:a@b.com'), - array('/foo/bar', '/foo/bar'), - ); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Property/ICalendar/DateTimeTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,359 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -use Sabre\VObject\Component; -use Sabre\VObject\Component\VCalendar; - - -class DateTimeTest extends \PHPUnit_Framework_TestCase { - - protected $vcal; - - function setUp() { - - $this->vcal = new VCalendar(); - - } - - function testSetDateTime() { - - $tz = new \DateTimeZone('Europe/Amsterdam'); - $dt = new \DateTime('1985-07-04 01:30:00', $tz); - $dt->setTimeZone($tz); - - $elem = $this->vcal->createProperty('DTSTART'); - $elem->setDateTime($dt); - - $this->assertEquals('19850704T013000', (string)$elem); - $this->assertEquals('Europe/Amsterdam', (string)$elem['TZID']); - $this->assertNull($elem['VALUE']); - - $this->assertTrue($elem->hasTime()); - - } - - function testSetDateTimeLOCAL() { - - $tz = new \DateTimeZone('Europe/Amsterdam'); - $dt = new \DateTime('1985-07-04 01:30:00', $tz); - $dt->setTimeZone($tz); - - $elem = $this->vcal->createProperty('DTSTART'); - $elem->setDateTime($dt, $isFloating = true); - - $this->assertEquals('19850704T013000', (string)$elem); - $this->assertNull($elem['TZID']); - - $this->assertTrue($elem->hasTime()); - } - - function testSetDateTimeUTC() { - - $tz = new \DateTimeZone('GMT'); - $dt = new \DateTime('1985-07-04 01:30:00', $tz); - $dt->setTimeZone($tz); - - $elem = $this->vcal->createProperty('DTSTART'); - $elem->setDateTime($dt); - - $this->assertEquals('19850704T013000Z', (string)$elem); - $this->assertNull($elem['TZID']); - - $this->assertTrue($elem->hasTime()); - } - - function testSetDateTimeLOCALTZ() { - - $tz = new \DateTimeZone('Europe/Amsterdam'); - $dt = new \DateTime('1985-07-04 01:30:00', $tz); - $dt->setTimeZone($tz); - - $elem = $this->vcal->createProperty('DTSTART'); - $elem->setDateTime($dt); - - $this->assertEquals('19850704T013000', (string)$elem); - $this->assertEquals('Europe/Amsterdam', (string)$elem['TZID']); - - $this->assertTrue($elem->hasTime()); - } - - function testSetDateTimeDATE() { - - $tz = new \DateTimeZone('Europe/Amsterdam'); - $dt = new \DateTime('1985-07-04 01:30:00', $tz); - $dt->setTimeZone($tz); - - $elem = $this->vcal->createProperty('DTSTART'); - $elem['VALUE'] = 'DATE'; - $elem->setDateTime($dt); - - $this->assertEquals('19850704', (string)$elem); - $this->assertNull($elem['TZID']); - $this->assertEquals('DATE', (string)$elem['VALUE']); - - $this->assertFalse($elem->hasTime()); - } - - function testSetValue() { - - $tz = new \DateTimeZone('Europe/Amsterdam'); - $dt = new \DateTime('1985-07-04 01:30:00', $tz); - $dt->setTimeZone($tz); - - $elem = $this->vcal->createProperty('DTSTART'); - $elem->setValue($dt); - - $this->assertEquals('19850704T013000', (string)$elem); - $this->assertEquals('Europe/Amsterdam', (string)$elem['TZID']); - $this->assertNull($elem['VALUE']); - - $this->assertTrue($elem->hasTime()); - - } - - function testSetValueArray() { - - $tz = new \DateTimeZone('Europe/Amsterdam'); - $dt1 = new \DateTime('1985-07-04 01:30:00', $tz); - $dt2 = new \DateTime('1985-07-04 02:30:00', $tz); - $dt1->setTimeZone($tz); - $dt2->setTimeZone($tz); - - $elem = $this->vcal->createProperty('DTSTART'); - $elem->setValue(array($dt1, $dt2)); - - $this->assertEquals('19850704T013000,19850704T023000', (string)$elem); - $this->assertEquals('Europe/Amsterdam', (string)$elem['TZID']); - $this->assertNull($elem['VALUE']); - - $this->assertTrue($elem->hasTime()); - - } - - function testSetParts() { - - $tz = new \DateTimeZone('Europe/Amsterdam'); - $dt1 = new \DateTime('1985-07-04 01:30:00', $tz); - $dt2 = new \DateTime('1985-07-04 02:30:00', $tz); - $dt1->setTimeZone($tz); - $dt2->setTimeZone($tz); - - $elem = $this->vcal->createProperty('DTSTART'); - $elem->setParts(array($dt1, $dt2)); - - $this->assertEquals('19850704T013000,19850704T023000', (string)$elem); - $this->assertEquals('Europe/Amsterdam', (string)$elem['TZID']); - $this->assertNull($elem['VALUE']); - - $this->assertTrue($elem->hasTime()); - - } - function testSetPartsStrings() { - - $dt1 = '19850704T013000Z'; - $dt2 = '19850704T023000Z'; - - $elem = $this->vcal->createProperty('DTSTART'); - $elem->setParts(array($dt1, $dt2)); - - $this->assertEquals('19850704T013000Z,19850704T023000Z', (string)$elem); - $this->assertNull($elem['VALUE']); - - $this->assertTrue($elem->hasTime()); - - } - - - function testGetDateTimeCached() { - - $tz = new \DateTimeZone('Europe/Amsterdam'); - $dt = new \DateTime('1985-07-04 01:30:00', $tz); - $dt->setTimeZone($tz); - - $elem = $this->vcal->createProperty('DTSTART'); - $elem->setDateTime($dt); - - $this->assertEquals($elem->getDateTime(), $dt); - - } - - function testGetDateTimeDateNULL() { - - $elem = $this->vcal->createProperty('DTSTART'); - $dt = $elem->getDateTime(); - - $this->assertNull($dt); - - } - - function testGetDateTimeDateDATE() { - - $elem = $this->vcal->createProperty('DTSTART','19850704'); - $dt = $elem->getDateTime(); - - $this->assertInstanceOf('DateTime', $dt); - $this->assertEquals('1985-07-04 00:00:00', $dt->format('Y-m-d H:i:s')); - - } - - function testGetDateTimeDateDATEReferenceTimeZone() { - - $elem = $this->vcal->createProperty('DTSTART','19850704'); - - $tz = new \DateTimeZone('America/Toronto'); - $dt = $elem->getDateTime($tz); - $dt->setTimeZone(new \DateTimeZone('UTC')); - - $this->assertInstanceOf('DateTime', $dt); - $this->assertEquals('1985-07-04 04:00:00', $dt->format('Y-m-d H:i:s')); - - } - - function testGetDateTimeDateFloating() { - - $elem = $this->vcal->createProperty('DTSTART','19850704T013000'); - $dt = $elem->getDateTime(); - - $this->assertInstanceOf('DateTime', $dt); - $this->assertEquals('1985-07-04 01:30:00', $dt->format('Y-m-d H:i:s')); - - } - - function testGetDateTimeDateFloatingReferenceTimeZone() { - - $elem = $this->vcal->createProperty('DTSTART','19850704T013000'); - - $tz = new \DateTimeZone('America/Toronto'); - $dt = $elem->getDateTime($tz); - $dt->setTimeZone(new \DateTimeZone('UTC')); - - $this->assertInstanceOf('DateTime', $dt); - $this->assertEquals('1985-07-04 05:30:00', $dt->format('Y-m-d H:i:s')); - - } - - function testGetDateTimeDateUTC() { - - $elem = $this->vcal->createProperty('DTSTART','19850704T013000Z'); - $dt = $elem->getDateTime(); - - $this->assertInstanceOf('DateTime', $dt); - $this->assertEquals('1985-07-04 01:30:00', $dt->format('Y-m-d H:i:s')); - $this->assertEquals('UTC', $dt->getTimeZone()->getName()); - - } - - function testGetDateTimeDateLOCALTZ() { - - $elem = $this->vcal->createProperty('DTSTART','19850704T013000'); - $elem['TZID'] = 'Europe/Amsterdam'; - - $dt = $elem->getDateTime(); - - $this->assertInstanceOf('DateTime', $dt); - $this->assertEquals('1985-07-04 01:30:00', $dt->format('Y-m-d H:i:s')); - $this->assertEquals('Europe/Amsterdam', $dt->getTimeZone()->getName()); - - } - - /** - * @expectedException LogicException - */ - function testGetDateTimeDateInvalid() { - - $elem = $this->vcal->createProperty('DTSTART','bla'); - $dt = $elem->getDateTime(); - - } - - function testGetDateTimeWeirdTZ() { - - $elem = $this->vcal->createProperty('DTSTART','19850704T013000'); - $elem['TZID'] = '/freeassociation.sourceforge.net/Tzfile/Europe/Amsterdam'; - - - $event = $this->vcal->createComponent('VEVENT'); - $event->add($elem); - - $timezone = $this->vcal->createComponent('VTIMEZONE'); - $timezone->TZID = '/freeassociation.sourceforge.net/Tzfile/Europe/Amsterdam'; - $timezone->{'X-LIC-LOCATION'} = 'Europe/Amsterdam'; - - $this->vcal->add($event); - $this->vcal->add($timezone); - - $dt = $elem->getDateTime(); - - $this->assertInstanceOf('DateTime', $dt); - $this->assertEquals('1985-07-04 01:30:00', $dt->format('Y-m-d H:i:s')); - $this->assertEquals('Europe/Amsterdam', $dt->getTimeZone()->getName()); - - } - - function testGetDateTimeBadTimeZone() { - - $default = date_default_timezone_get(); - date_default_timezone_set('Canada/Eastern'); - - $elem = $this->vcal->createProperty('DTSTART','19850704T013000'); - $elem['TZID'] = 'Moon'; - - - $event = $this->vcal->createComponent('VEVENT'); - $event->add($elem); - - $timezone = $this->vcal->createComponent('VTIMEZONE'); - $timezone->TZID = 'Moon'; - $timezone->{'X-LIC-LOCATION'} = 'Moon'; - - - $this->vcal->add($event); - $this->vcal->add($timezone); - - $dt = $elem->getDateTime(); - - $this->assertInstanceOf('DateTime', $dt); - $this->assertEquals('1985-07-04 01:30:00', $dt->format('Y-m-d H:i:s')); - $this->assertEquals('Canada/Eastern', $dt->getTimeZone()->getName()); - date_default_timezone_set($default); - - } - - function testUpdateValueParameter() { - - $dtStart = $this->vcal->createProperty('DTSTART', new \DateTime('2013-06-07 15:05:00')); - $dtStart['VALUE'] = 'DATE'; - - $this->assertEquals("DTSTART;VALUE=DATE:20130607\r\n", $dtStart->serialize()); - - } - - function testValidate() { - - $exDate = $this->vcal->createProperty('EXDATE', '-00011130T143000Z'); - $messages = $exDate->validate(); - $this->assertEquals(1, count($messages)); - $this->assertEquals(3, $messages[0]['level']); - - } - - /** - * This issue was discovered on the sabredav mailing list. - */ - function testCreateDatePropertyThroughAdd() { - - $vcal = new VCalendar(); - $vevent = $vcal->add('VEVENT'); - - $dtstart = $vevent->add( - 'DTSTART', - new \DateTime('2014-03-07'), - array('VALUE' => 'DATE') - ); - - $this->assertEquals("DTSTART;VALUE=DATE:20140307\r\n", $dtstart->serialize()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Property/ICalendar/DurationTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,20 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -use Sabre\VObject\Component\VCalendar; -use Sabre\VObject\Component\VEvent; - -class DurationTest extends \PHPUnit_Framework_TestCase { - - function testGetDateInterval() { - - $vcal = new VCalendar(); - $event = $vcal->add('VEVENT', array('DURATION' => array('PT1H'))); - - $this->assertEquals( - new \DateInterval('PT1H'), - $event->{'DURATION'}->getDateInterval() - ); - } -}
--- a/vendor/sabre/vobject/tests/VObject/Property/ICalendar/RecurTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,46 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\ICalendar; - -use Sabre\VObject\Component\VCalendar; - -class RecurTest extends \PHPUnit_Framework_TestCase { - - function testParts() { - - $vcal = new VCalendar(); - $recur = $vcal->add('RRULE', 'FREQ=Daily'); - - $this->assertInstanceOf('Sabre\VObject\Property\ICalendar\Recur', $recur); - - $this->assertEquals(array('FREQ'=>'DAILY'), $recur->getParts()); - $recur->setParts(array('freq'=>'MONTHLY')); - - $this->assertEquals(array('FREQ'=>'MONTHLY'), $recur->getParts()); - - } - - /** - * @expectedException \InvalidArgumentException - */ - function testSetValueBadVal() { - - $vcal = new VCalendar(); - $recur = $vcal->add('RRULE', 'FREQ=Daily'); - $recur->setValue(new \Exception()); - - } - - function testSetSubParts() { - - $vcal = new VCalendar(); - $recur = $vcal->add('RRULE', array('FREQ'=>'DAILY', 'BYDAY'=>'mo,tu', 'BYMONTH' => array(0,1))); - - $this->assertEquals(array( - 'FREQ'=>'DAILY', - 'BYDAY' => array('MO','TU'), - 'BYMONTH' => array(0,1), - ), $recur->getParts()); - - } -}
--- a/vendor/sabre/vobject/tests/VObject/Property/TextTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,96 +0,0 @@ -<?php - -namespace Sabre\VObject\Property; - -use Sabre\VObject\Component\VCard; - -class TextTest extends \PHPUnit_Framework_TestCase { - - function assertVCard21serialization($propValue, $expected) { - - $doc = new VCard(array( - 'VERSION'=>'2.1', - 'PROP' => $propValue - ), false); - - // Adding quoted-printable, because we're testing if it gets removed - // automatically. - $doc->PROP['ENCODING'] = 'QUOTED-PRINTABLE'; - $doc->PROP['P1'] = 'V1'; - - - $output = $doc->serialize(); - - - $this->assertEquals("BEGIN:VCARD\r\nVERSION:2.1\r\n$expected\r\nEND:VCARD\r\n", $output); - - } - - function testSerializeVCard21() { - - $this->assertVCard21Serialization( - 'f;oo', - 'PROP;P1=V1:f;oo' - ); - - } - - function testSerializeVCard21Array() { - - $this->assertVCard21Serialization( - array('f;oo','bar'), - 'PROP;P1=V1:f\;oo;bar' - ); - - } - function testSerializeVCard21Fold() { - - $this->assertVCard21Serialization( - str_repeat('x',80), - 'PROP;P1=V1:' . str_repeat('x',64) . "\r\n " . str_repeat('x',16) - ); - - } - - - - function testSerializeQuotedPrintable() { - - $this->assertVCard21Serialization( - "foo\r\nbar", - 'PROP;P1=V1;ENCODING=QUOTED-PRINTABLE:foo=0D=0Abar' - ); - } - - function testSerializeQuotedPrintableFold() { - - $this->assertVCard21Serialization( - "foo\r\nbarxxxxxxxxxxxxxxxxxxxxxxxxxxxxx", - "PROP;P1=V1;ENCODING=QUOTED-PRINTABLE:foo=0D=0Abarxxxxxxxxxxxxxxxxxxxxxxxxxx=\r\n xxx" - ); - - } - - function testValidateMinimumPropValue() { - - $vcard = <<<IN -BEGIN:VCARD -VERSION:4.0 -UID:foo -FN:Hi! -N:A -END:VCARD -IN; - - $vcard = \Sabre\VObject\Reader::read($vcard); - $this->assertEquals(1, count($vcard->validate())); - - $this->assertEquals(1, count($vcard->N->getParts())); - - $vcard->validate(\Sabre\VObject\Node::REPAIR); - - $this->assertEquals(5, count($vcard->N->getParts())); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Property/VCard/DateAndOrTimeTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,233 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\VCard; - -use - Sabre\VObject, - Sabre\VObject\Reader; - -class DateAndOrTimeTest extends \PHPUnit_Framework_TestCase { - - /** - * @dataProvider dates - */ - function testGetJsonValue($input, $output) { - - $vcard = new VObject\Component\VCard(); - $prop = $vcard->createProperty('BDAY', $input); - - $this->assertEquals(array($output), $prop->getJsonValue()); - - } - - function dates() { - - return array( - array( - "19961022T140000", - "1996-10-22T14:00:00", - ), - array( - "--1022T1400", - "--10-22T14:00", - ), - array( - "---22T14", - "---22T14", - ), - array( - "19850412", - "1985-04-12", - ), - array( - "1985-04", - "1985-04", - ), - array( - "1985", - "1985", - ), - array( - "--0412", - "--04-12", - ), - array( - "T102200", - "T10:22:00", - ), - array( - "T1022", - "T10:22", - ), - array( - "T10", - "T10", - ), - array( - "T-2200", - "T-22:00", - ), - array( - "T102200Z", - "T10:22:00Z", - ), - array( - "T102200-0800", - "T10:22:00-0800", - ), - array( - "T--00", - "T--00", - ), - ); - - } - - public function testSetParts() { - - $vcard = new VObject\Component\VCard(); - - $prop = $vcard->createProperty('BDAY'); - $prop->setParts(array( - new \DateTime('2014-04-02 18:37:00') - )); - - $this->assertEquals('20140402T183700Z', $prop->getValue()); - - } - - /** - * @expectedException InvalidArgumentException - */ - public function testSetPartsTooMany() { - - $vcard = new VObject\Component\VCard(); - - $prop = $vcard->createProperty('BDAY'); - $prop->setParts(array( - 1, - 2 - )); - - } - - public function testSetPartsString() { - - $vcard = new VObject\Component\VCard(); - - $prop = $vcard->createProperty('BDAY'); - $prop->setParts(array( - "20140402T183700Z" - )); - - $this->assertEquals('20140402T183700Z', $prop->getValue()); - - } - - public function testSetValueDateTime() { - - $vcard = new VObject\Component\VCard(); - - $prop = $vcard->createProperty('BDAY'); - $prop->setValue( - new \DateTime('2014-04-02 18:37:00') - ); - - $this->assertEquals('20140402T183700Z', $prop->getValue()); - - } - - public function testSetDateTimeOffset() { - - $vcard = new VObject\Component\VCard(); - - $prop = $vcard->createProperty('BDAY'); - $prop->setValue( - new \DateTime('2014-04-02 18:37:00', new \DateTimeZone('America/Toronto')) - ); - - $this->assertEquals('20140402T183700-0400', $prop->getValue()); - - } - - public function testGetDateTime() { - - $datetime = new \DateTime('2014-04-02 18:37:00', new \DateTimeZone('America/Toronto')); - - $vcard = new VObject\Component\VCard(); - $prop = $vcard->createProperty('BDAY', $datetime); - - $dt = $prop->getDateTime(); - $this->assertEquals('2014-04-02T18:37:00-04:00', $dt->format('c'), "For some reason this one failed. Current default timezone is: " . date_default_timezone_get()); - - } - - public function testGetDateIncomplete() { - - $datetime = '--0407'; - - $vcard = new VObject\Component\VCard(); - $prop = $vcard->add('BDAY', $datetime); - - $dt = $prop->getDateTime(); - // Note: if the year changes between the last line and the next line of - // code, this test may fail. - // - // If that happens, head outside and have a drink. - $current = new \DateTime('now'); - $year = $current->format('Y'); - - $this->assertEquals($year . '0407', $dt->format('Ymd')); - - } - - public function testGetDateIncompleteFromVCard() { - - $vcard = <<<VCF -BEGIN:VCARD -VERSION:4.0 -BDAY:--0407 -END:VCARD -VCF; - $vcard = Reader::read($vcard); - $prop = $vcard->BDAY; - - $dt = $prop->getDateTime(); - // Note: if the year changes between the last line and the next line of - // code, this test may fail. - // - // If that happens, head outside and have a drink. - $current = new \DateTime('now'); - $year = $current->format('Y'); - - $this->assertEquals($year . '0407', $dt->format('Ymd')); - - } - - public function testValidate() { - - $datetime = '--0407'; - - $vcard = new VObject\Component\VCard(); - $prop = $vcard->add('BDAY', $datetime); - - $this->assertEquals(array(), $prop->validate()); - - } - - public function testValidateBroken() { - - $datetime = '123'; - - $vcard = new VObject\Component\VCard(); - $prop = $vcard->add('BDAY', $datetime); - - $this->assertEquals(array(array( - 'level' => 3, - 'message' => 'The supplied value (123) is not a correct DATE-AND-OR-TIME property', - 'node' => $prop, - )), $prop->validate()); - - } -} -
--- a/vendor/sabre/vobject/tests/VObject/Property/VCard/LanguageTagTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,27 +0,0 @@ -<?php - -namespace Sabre\VObject\Property\VCard; - -use Sabre\VObject; - -class LanguageTagTest extends \PHPUnit_Framework_TestCase { - - function testMimeDir() { - - $input = "BEGIN:VCARD\r\nVERSION:4.0\r\nLANG:nl\r\nEND:VCARD\r\n"; - $mimeDir = new VObject\Parser\MimeDir($input); - - $result = $mimeDir->parse($input); - - $this->assertInstanceOf('Sabre\VObject\Property\VCard\LanguageTag', $result->LANG); - - $this->assertEquals('nl', $result->LANG->getValue()); - - $this->assertEquals( - $input, - $result->serialize() - ); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/PropertyTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,360 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - Sabre\VObject\Component\VCalendar; - -class PropertyTest extends \PHPUnit_Framework_TestCase { - - public function testToString() { - - $cal = new VCalendar(); - - $property = $cal->createProperty('propname','propvalue'); - $this->assertEquals('PROPNAME', $property->name); - $this->assertEquals('propvalue', $property->__toString()); - $this->assertEquals('propvalue', (string)$property); - $this->assertEquals('propvalue', $property->getValue()); - - } - - public function testCreate() { - - $cal = new VCalendar(); - - $params = array( - 'param1' => 'value1', - 'param2' => 'value2', - ); - - $property = $cal->createProperty('propname','propvalue', $params); - - $this->assertEquals('value1', $property['param1']->getValue()); - $this->assertEquals('value2', $property['param2']->getValue()); - - } - - public function testSetValue() { - - $cal = new VCalendar(); - - $property = $cal->createProperty('propname','propvalue'); - $property->setValue('value2'); - - $this->assertEquals('PROPNAME', $property->name); - $this->assertEquals('value2', $property->__toString()); - - } - - public function testParameterExists() { - - $cal = new VCalendar(); - $property = $cal->createProperty('propname','propvalue'); - $property['paramname'] = 'paramvalue'; - - $this->assertTrue(isset($property['PARAMNAME'])); - $this->assertTrue(isset($property['paramname'])); - $this->assertFalse(isset($property['foo'])); - - } - - public function testParameterGet() { - - $cal = new VCalendar(); - $property = $cal->createProperty('propname','propvalue'); - $property['paramname'] = 'paramvalue'; - - $this->assertInstanceOf('Sabre\\VObject\\Parameter',$property['paramname']); - - } - - public function testParameterNotExists() { - - $cal = new VCalendar(); - $property = $cal->createProperty('propname','propvalue'); - $property['paramname'] = 'paramvalue'; - - $this->assertInternalType('null',$property['foo']); - - } - - public function testParameterMultiple() { - - $cal = new VCalendar(); - $property = $cal->createProperty('propname','propvalue'); - $property['paramname'] = 'paramvalue'; - $property->add('paramname', 'paramvalue'); - - $this->assertInstanceOf('Sabre\\VObject\\Parameter',$property['paramname']); - $this->assertEquals(2,count($property['paramname']->getParts())); - - } - - public function testSetParameterAsString() { - - $cal = new VCalendar(); - $property = $cal->createProperty('propname','propvalue'); - $property['paramname'] = 'paramvalue'; - - $this->assertEquals(1,count($property->parameters())); - $this->assertInstanceOf('Sabre\\VObject\\Parameter', $property->parameters['PARAMNAME']); - $this->assertEquals('PARAMNAME',$property->parameters['PARAMNAME']->name); - $this->assertEquals('paramvalue',$property->parameters['PARAMNAME']->getValue()); - - } - - public function testUnsetParameter() { - - $cal = new VCalendar(); - $property = $cal->createProperty('propname','propvalue'); - $property['paramname'] = 'paramvalue'; - - unset($property['PARAMNAME']); - $this->assertEquals(0,count($property->parameters())); - - } - - public function testSerialize() { - - $cal = new VCalendar(); - $property = $cal->createProperty('propname','propvalue'); - - $this->assertEquals("PROPNAME:propvalue\r\n",$property->serialize()); - - } - - public function testSerializeParam() { - - $cal = new VCalendar(); - $property = $cal->createProperty('propname','propvalue', array( - 'paramname' => 'paramvalue', - 'paramname2' => 'paramvalue2', - )); - - $this->assertEquals("PROPNAME;PARAMNAME=paramvalue;PARAMNAME2=paramvalue2:propvalue\r\n",$property->serialize()); - - } - - public function testSerializeNewLine() { - - $cal = new VCalendar(); - $property = $cal->createProperty('SUMMARY',"line1\nline2"); - - $this->assertEquals("SUMMARY:line1\\nline2\r\n",$property->serialize()); - - } - - public function testSerializeLongLine() { - - $cal = new VCalendar(); - $value = str_repeat('!',200); - $property = $cal->createProperty('propname',$value); - - $expected = "PROPNAME:" . str_repeat('!',66) . "\r\n " . str_repeat('!',74) . "\r\n " . str_repeat('!',60) . "\r\n"; - - $this->assertEquals($expected,$property->serialize()); - - } - - public function testSerializeUTF8LineFold() { - - $cal = new VCalendar(); - $value = str_repeat('!',65) . "\xc3\xa4bla"; // inserted umlaut-a - $property = $cal->createProperty('propname', $value); - $expected = "PROPNAME:" . str_repeat('!',65) . "\r\n \xc3\xa4bla\r\n"; - $this->assertEquals($expected, $property->serialize()); - - } - - public function testGetIterator() { - - $cal = new VCalendar(); - $it = new ElementList(array()); - $property = $cal->createProperty('propname','propvalue'); - $property->setIterator($it); - $this->assertEquals($it,$property->getIterator()); - - } - - - public function testGetIteratorDefault() { - - $cal = new VCalendar(); - $property = $cal->createProperty('propname','propvalue'); - $it = $property->getIterator(); - $this->assertTrue($it instanceof ElementList); - $this->assertEquals(1,count($it)); - - } - - function testAddScalar() { - - $cal = new VCalendar(); - $property = $cal->createProperty('EMAIL'); - - $property->add('myparam','value'); - - $this->assertEquals(1, count($property->parameters())); - - $this->assertTrue($property->parameters['MYPARAM'] instanceof Parameter); - $this->assertEquals('MYPARAM',$property->parameters['MYPARAM']->name); - $this->assertEquals('value',$property->parameters['MYPARAM']->getValue()); - - } - - function testAddParameter() { - - $cal = new VCalendar(); - $prop = $cal->createProperty('EMAIL'); - - $prop->add('MYPARAM','value'); - - $this->assertEquals(1, count($prop->parameters())); - $this->assertEquals('MYPARAM',$prop['myparam']->name); - - } - - function testAddParameterTwice() { - - $cal = new VCalendar(); - $prop = $cal->createProperty('EMAIL'); - - $prop->add('MYPARAM', 'value1'); - $prop->add('MYPARAM', 'value2'); - - $this->assertEquals(1, count($prop->parameters)); - $this->assertEquals(2, count($prop->parameters['MYPARAM']->getParts())); - - $this->assertEquals('MYPARAM',$prop['MYPARAM']->name); - - } - - - function testClone() { - - $cal = new VCalendar(); - $property = $cal->createProperty('EMAIL','value'); - $property['FOO'] = 'BAR'; - - $property2 = clone $property; - - $property['FOO'] = 'BAZ'; - $this->assertEquals('BAR', (string)$property2['FOO']); - - } - - function testCreateParams() { - - $cal = new VCalendar(); - $property = $cal->createProperty('X-PROP','value', array( - 'param1' => 'value1', - 'param2' => array('value2', 'value3') - )); - - $this->assertEquals(1, count($property['PARAM1']->getParts())); - $this->assertEquals(2, count($property['PARAM2']->getParts())); - - } - - function testValidateNonUTF8() { - - $calendar = new VCalendar(); - $property = $calendar->createProperty('X-PROP', "Bla\x00"); - $result = $property->validate(Property::REPAIR); - - $this->assertEquals('Property contained a control character (0x00)', $result[0]['message']); - $this->assertEquals('Bla', $property->getValue()); - - } - - function testValidateControlChars() { - - $s = "chars["; - foreach (array( - 0x7F, 0x5E, 0x5C, 0x3B, 0x3A, 0x2C, 0x22, 0x20, - 0x1F, 0x1E, 0x1D, 0x1C, 0x1B, 0x1A, 0x19, 0x18, - 0x17, 0x16, 0x15, 0x14, 0x13, 0x12, 0x11, 0x10, - 0x0F, 0x0E, 0x0D, 0x0C, 0x0B, 0x0A, 0x09, 0x08, - 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01, 0x00, - ) as $c) { - $s .= sprintf('%02X(%c)', $c, $c); - } - $s .= "]end"; - - $calendar = new VCalendar(); - $property = $calendar->createProperty('X-PROP', $s); - $result = $property->validate(Property::REPAIR); - - $this->assertEquals('Property contained a control character (0x7f)', $result[0]['message']); - $this->assertEquals("chars[7F()5E(^)5C(\\\\)3B(\\;)3A(:)2C(\\,)22(\")20( )1F()1E()1D()1C()1B()1A()19()18()17()16()15()14()13()12()11()10()0F()0E()0D()0C()0B()0A(\\n)09( )08()07()06()05()04()03()02()01()00()]end", $property->getRawMimeDirValue()); - - } - - - function testValidateBadPropertyName() { - - $calendar = new VCalendar(); - $property = $calendar->createProperty("X_*&PROP*", "Bla"); - $result = $property->validate(Property::REPAIR); - - $this->assertEquals($result[0]['message'], 'The propertyname: X_*&PROP* contains invalid characters. Only A-Z, 0-9 and - are allowed'); - $this->assertEquals('X-PROP', $property->name); - - } - - function testGetValue() { - - $calendar = new VCalendar(); - $property = $calendar->createProperty("SUMMARY", null); - $this->assertEquals(array(), $property->getParts()); - $this->assertNull($property->getValue()); - - $property->setValue(array()); - $this->assertEquals(array(), $property->getParts()); - $this->assertNull($property->getValue()); - - $property->setValue(array(1)); - $this->assertEquals(array(1), $property->getParts()); - $this->assertEquals(1, $property->getValue()); - - $property->setValue(array(1,2)); - $this->assertEquals(array(1,2), $property->getParts()); - $this->assertEquals('1,2', $property->getValue()); - - $property->setValue('str'); - $this->assertEquals(array('str'), $property->getParts()); - $this->assertEquals('str', $property->getValue()); - } - - /** - * ElementList should reject this. - * - * @expectedException \LogicException - */ - public function testArrayAccessSetInt() { - - $calendar = new VCalendar(); - $property = $calendar->createProperty("X-PROP", null); - - $calendar->add($property); - $calendar->{'X-PROP'}[0] = 'Something!'; - - } - - /** - * ElementList should reject this. - * - * @expectedException \LogicException - */ - public function testArrayAccessUnsetInt() { - - $calendar = new VCalendar(); - $property = $calendar->createProperty("X-PROP", null); - - $calendar->add($property); - unset($calendar->{'X-PROP'}[0]); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/ReaderTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,449 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class ReaderTest extends \PHPUnit_Framework_TestCase { - - function testReadComponent() { - - $data = "BEGIN:VCALENDAR\r\nEND:VCALENDAR"; - - $result = Reader::read($data); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCALENDAR', $result->name); - $this->assertEquals(0, count($result->children)); - - } - function testReadStream() { - - $data = "BEGIN:VCALENDAR\r\nEND:VCALENDAR"; - - $stream = fopen('php://memory', 'r+'); - fwrite($stream, $data); - rewind($stream); - - $result = Reader::read($stream); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCALENDAR', $result->name); - $this->assertEquals(0, count($result->children)); - - } - - function testReadComponentUnixNewLine() { - - $data = "BEGIN:VCALENDAR\nEND:VCALENDAR"; - - $result = Reader::read($data); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCALENDAR', $result->name); - $this->assertEquals(0, count($result->children)); - - } - - function testReadComponentLineFold() { - - $data = "BEGIN:\r\n\tVCALENDAR\r\nE\r\n ND:VCALENDAR"; - - $result = Reader::read($data); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCALENDAR', $result->name); - $this->assertEquals(0, count($result->children)); - - } - - /** - * @expectedException Sabre\VObject\ParseException - */ - function testReadCorruptComponent() { - - $data = "BEGIN:VCALENDAR\r\nEND:FOO"; - - $result = Reader::read($data); - - } - - /** - * @expectedException Sabre\VObject\ParseException - */ - function testReadCorruptSubComponent() { - - $data = "BEGIN:VCALENDAR\r\nBEGIN:VEVENT\r\nEND:FOO\r\nEND:VCALENDAR"; - - $result = Reader::read($data); - - } - - function testReadProperty() { - - $data = "BEGIN:VCALENDAR\r\nSUMMARY:propValue\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->SUMMARY; - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('SUMMARY', $result->name); - $this->assertEquals('propValue', $result->getValue()); - - } - - function testReadPropertyWithNewLine() { - - $data = "BEGIN:VCALENDAR\r\nSUMMARY:Line1\\nLine2\\NLine3\\\\Not the 4th line!\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->SUMMARY; - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('SUMMARY', $result->name); - $this->assertEquals("Line1\nLine2\nLine3\\Not the 4th line!", $result->getValue()); - - } - - function testReadMappedProperty() { - - $data = "BEGIN:VCALENDAR\r\nDTSTART:20110529\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->DTSTART; - $this->assertInstanceOf('Sabre\\VObject\\Property\\ICalendar\\DateTime', $result); - $this->assertEquals('DTSTART', $result->name); - $this->assertEquals('20110529', $result->getValue()); - - } - - function testReadMappedPropertyGrouped() { - - $data = "BEGIN:VCALENDAR\r\nfoo.DTSTART:20110529\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->DTSTART; - $this->assertInstanceOf('Sabre\\VObject\\Property\\ICalendar\\DateTime', $result); - $this->assertEquals('DTSTART', $result->name); - $this->assertEquals('20110529', $result->getValue()); - - } - - /** - * @expectedException Sabre\VObject\ParseException - */ - function testReadBrokenLine() { - - $data = "BEGIN:VCALENDAR\r\nPROPNAME;propValue"; - $result = Reader::read($data); - - } - - function testReadPropertyInComponent() { - - $data = array( - "BEGIN:VCALENDAR", - "PROPNAME:propValue", - "END:VCALENDAR" - ); - - $result = Reader::read(implode("\r\n",$data)); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCALENDAR', $result->name); - $this->assertEquals(1, count($result->children())); - $this->assertInstanceOf('Sabre\\VObject\\Property', $result->children[0]); - $this->assertEquals('PROPNAME', $result->children[0]->name); - $this->assertEquals('propValue', $result->children[0]->getValue()); - - } - - function testReadNestedComponent() { - - $data = array( - "BEGIN:VCALENDAR", - "BEGIN:VTIMEZONE", - "BEGIN:DAYLIGHT", - "END:DAYLIGHT", - "END:VTIMEZONE", - "END:VCALENDAR" - ); - - $result = Reader::read(implode("\r\n",$data)); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCALENDAR', $result->name); - $this->assertEquals(1, count($result->children())); - $this->assertInstanceOf('Sabre\\VObject\\Component', $result->children[0]); - $this->assertEquals('VTIMEZONE', $result->children[0]->name); - $this->assertEquals(1, count($result->children[0]->children())); - $this->assertInstanceOf('Sabre\\VObject\\Component', $result->children[0]->children[0]); - $this->assertEquals('DAYLIGHT', $result->children[0]->children[0]->name); - - - } - - function testReadPropertyParameter() { - - $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=paramvalue:propValue\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->PROPNAME; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('PROPNAME', $result->name); - $this->assertEquals('propValue', $result->getValue()); - $this->assertEquals(1, count($result->parameters())); - $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); - $this->assertEquals('paramvalue', $result->parameters['PARAMNAME']->getValue()); - - } - - function testReadPropertyRepeatingParameter() { - - $data = "BEGIN:VCALENDAR\r\nPROPNAME;N=1;N=2;N=3,4;N=\"5\",6;N=\"7,8\";N=9,10;N=^'11^':propValue\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->PROPNAME; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('PROPNAME', $result->name); - $this->assertEquals('propValue', $result->getValue()); - $this->assertEquals(1, count($result->parameters())); - $this->assertEquals('N', $result->parameters['N']->name); - $this->assertEquals('1,2,3,4,5,6,7,8,9,10,"11"', $result->parameters['N']->getValue()); - $this->assertEquals(array(1,2,3,4,5,6,"7,8",9,10,'"11"'), $result->parameters['N']->getParts()); - - } - - function testReadPropertyRepeatingNamelessGuessedParameter() { - $data = "BEGIN:VCALENDAR\r\nPROPNAME;WORK;VOICE;PREF:propValue\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->PROPNAME; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('PROPNAME', $result->name); - $this->assertEquals('propValue', $result->getValue()); - $this->assertEquals(1, count($result->parameters())); - $this->assertEquals('TYPE', $result->parameters['TYPE']->name); - $this->assertEquals('WORK,VOICE,PREF', $result->parameters['TYPE']->getValue()); - $this->assertEquals(array('WORK', 'VOICE', 'PREF'), $result->parameters['TYPE']->getParts()); - - } - - function testReadPropertyNoName() { - - $data = "BEGIN:VCALENDAR\r\nPROPNAME;PRODIGY:propValue\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->PROPNAME; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('PROPNAME', $result->name); - $this->assertEquals('propValue', $result->getValue()); - $this->assertEquals(1, count($result->parameters())); - $this->assertEquals('TYPE', $result->parameters['TYPE']->name); - $this->assertTrue($result->parameters['TYPE']->noName); - $this->assertEquals('PRODIGY', $result->parameters['TYPE']); - - } - - function testReadPropertyParameterExtraColon() { - - $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=paramvalue:propValue:anotherrandomstring\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->PROPNAME; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('PROPNAME', $result->name); - $this->assertEquals('propValue:anotherrandomstring', $result->getValue()); - $this->assertEquals(1, count($result->parameters())); - $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); - $this->assertEquals('paramvalue', $result->parameters['PARAMNAME']->getValue()); - - } - - function testReadProperty2Parameters() { - - $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=paramvalue;PARAMNAME2=paramvalue2:propValue\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->PROPNAME; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('PROPNAME', $result->name); - $this->assertEquals('propValue', $result->getValue()); - $this->assertEquals(2, count($result->parameters())); - $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); - $this->assertEquals('paramvalue', $result->parameters['PARAMNAME']->getValue()); - $this->assertEquals('PARAMNAME2', $result->parameters['PARAMNAME2']->name); - $this->assertEquals('paramvalue2', $result->parameters['PARAMNAME2']->getValue()); - - } - - function testReadPropertyParameterQuoted() { - - $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=\"paramvalue\":propValue\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->PROPNAME; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('PROPNAME', $result->name); - $this->assertEquals('propValue', $result->getValue()); - $this->assertEquals(1, count($result->parameters())); - $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); - $this->assertEquals('paramvalue', $result->parameters['PARAMNAME']->getValue()); - - } - - function testReadPropertyParameterNewLines() { - - $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=paramvalue1^nvalue2^^nvalue3:propValue\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $result = $result->propname; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('PROPNAME', $result->name); - $this->assertEquals('propValue', $result->getValue()); - - $this->assertEquals(1, count($result->parameters())); - $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); - $this->assertEquals("paramvalue1\nvalue2^nvalue3", $result->parameters['PARAMNAME']->getValue()); - - } - - function testReadPropertyParameterQuotedColon() { - - $data = "BEGIN:VCALENDAR\r\nPROPNAME;PARAMNAME=\"param:value\":propValue\r\nEND:VCALENDAR"; - $result = Reader::read($data); - $result = $result->propname; - - $this->assertInstanceOf('Sabre\\VObject\\Property', $result); - $this->assertEquals('PROPNAME', $result->name); - $this->assertEquals('propValue', $result->getValue()); - $this->assertEquals(1, count($result->parameters())); - $this->assertEquals('PARAMNAME', $result->parameters['PARAMNAME']->name); - $this->assertEquals('param:value', $result->parameters['PARAMNAME']->getValue()); - - } - - function testReadForgiving() { - - $data = array( - "BEGIN:VCALENDAR", - "X_PROP:propValue", - "END:VCALENDAR" - ); - - $caught = false; - try { - $result = Reader::read(implode("\r\n",$data)); - } catch (ParseException $e) { - $caught = true; - } - - $this->assertEquals(true, $caught); - - $result = Reader::read(implode("\r\n",$data), Reader::OPTION_FORGIVING); - - $expected = implode("\r\n", array( - "BEGIN:VCALENDAR", - "X_PROP:propValue", - "END:VCALENDAR", - "" - )); - - $this->assertEquals($expected, $result->serialize()); - - } - - function testReadWithInvalidLine() { - - $data = array( - "BEGIN:VCALENDAR", - "DESCRIPTION:propValue", - "Yes, we've actually seen a file with non-idented property values on multiple lines", - "END:VCALENDAR" - ); - - $caught = false; - try { - $result = Reader::read(implode("\r\n",$data)); - } catch (ParseException $e) { - $caught = true; - } - - $this->assertEquals(true, $caught); - - $result = Reader::read(implode("\r\n",$data), Reader::OPTION_IGNORE_INVALID_LINES); - - $expected = implode("\r\n", array( - "BEGIN:VCALENDAR", - "DESCRIPTION:propValue", - "END:VCALENDAR", - "" - )); - - $this->assertEquals($expected, $result->serialize()); - - } - - /** - * Reported as Issue 32. - * - * @expectedException \Sabre\VObject\ParseException - */ - public function testReadIncompleteFile() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:1.0 -BEGIN:VEVENT -X-FUNAMBOL-FOLDER:DEFAULT_FOLDER -X-FUNAMBOL-ALLDAY:0 -DTSTART:20111017T110000Z -DTEND:20111017T123000Z -X-MICROSOFT-CDO-BUSYSTATUS:BUSY -CATEGORIES: -LOCATION;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:Netviewer Meeting -PRIORITY:1 -STATUS:3 -X-MICROSOFT-CDO-REPLYTIME:20111017T064200Z -SUMMARY;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:Kopieren: test -CLASS:PUBLIC -AALARM: -RRULE: -X-FUNAMBOL-BILLINGINFO: -X-FUNAMBOL-COMPANIES: -X-FUNAMBOL-MILEAGE: -X-FUNAMBOL-NOAGING:0 -ATTENDEE;STATUS=NEEDS ACTION;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:'Heino' heino@test.com -ATTENDEE;STATUS=NEEDS ACTION;ENCODING=QUOTED-PRINTABLE;CHARSET=UTF-8:'Markus' test@test.com -ATTENDEE;STATUS=NEEDS AC -ICS; - - Reader::read($input); - - } - - /** - * @expectedException \InvalidArgumentException - */ - public function testReadBrokenInput() { - - Reader::read(false); - - } - - public function testReadBOM() { - - $data = chr(0xef) . chr(0xbb) . chr(0xbf) . "BEGIN:VCALENDAR\r\nEND:VCALENDAR"; - $result = Reader::read($data); - - $this->assertInstanceOf('Sabre\\VObject\\Component', $result); - $this->assertEquals('VCALENDAR', $result->name); - $this->assertEquals(0, count($result->children)); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/ByMonthInDailyTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,58 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - DateTime; - -class RecurrenceIteratorByMonthInDailyTest extends \PHPUnit_Framework_TestCase { - - /** - * This tests the expansion of dates with DAILY frequency in RRULE with BYMONTH restrictions - */ - function testExpand() { - - $ics = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Apple Inc.//iCal 4.0.4//EN -CALSCALE:GREGORIAN -BEGIN:VEVENT -TRANSP:OPAQUE -DTEND:20070925T183000Z -UID:uuid -DTSTAMP:19700101T000000Z -LOCATION: -DESCRIPTION: -STATUS:CONFIRMED -SEQUENCE:18 -SUMMARY:Stuff -DTSTART:20070925T160000Z -CREATED:20071004T144642Z -RRULE:FREQ=DAILY;BYMONTH=9,10;BYDAY=SU -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($ics); - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCalendar', $vcal); - - $vcal->expand(new DateTime('2013-09-28'), new DateTime('2014-09-11')); - - foreach ($vcal->VEVENT as $event) { - $dates[] = $event->DTSTART->getValue(); - } - - $expectedDates = array( - "20130929T160000Z", - "20131006T160000Z", - "20131013T160000Z", - "20131020T160000Z", - "20131027T160000Z", - "20140907T160000Z" - ); - - $this->assertEquals($expectedDates, $dates, 'Recursed dates are restricted by month'); - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/FifthTuesdayProblemTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,54 +0,0 @@ -<?php - -namespace Sabre\VObject\Recur\EventIterator; - -use Sabre\VObject\Recur; -use Sabre\VObject\Reader; - -class FifthTuesdayProblemTest extends \PHPUnit_Framework_TestCase { - - /** - * A pretty slow test. Had to be marked as 'medium' for phpunit to not die - * after 1 second. Would be good to optimize later. - * - * @medium - */ - function testGetDTEnd() { - - $ics = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Apple Inc.//iCal 4.0.4//EN -CALSCALE:GREGORIAN -BEGIN:VEVENT -TRANSP:OPAQUE -DTEND;TZID=America/New_York:20070925T170000 -UID:uuid -DTSTAMP:19700101T000000Z -LOCATION: -DESCRIPTION: -STATUS:CONFIRMED -SEQUENCE:18 -SUMMARY:Stuff -DTSTART;TZID=America/New_York:20070925T160000 -CREATED:20071004T144642Z -RRULE:FREQ=MONTHLY;INTERVAL=1;UNTIL=20071030T035959Z;BYDAY=5TU -END:VEVENT -END:VCALENDAR -ICS; - - $vObject = Reader::read($ics); - $it = new Recur\EventIterator($vObject, (string)$vObject->VEVENT->UID); - - while($it->valid()) { - $it->next(); - } - - // If we got here, it means we were successful. The bug that was in the - // system before would fail on the 5th tuesday of the month, if the 5th - // tuesday did not exist. - $this->assertTrue(true); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/IncorrectExpandTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,62 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - DateTime, - DateTimeZone; - -/** - * This is a unittest for Issue #53. - */ -class RecurrenceIteratorIncorrectExpandTest extends \PHPUnit_Framework_TestCase { - - function testExpand() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foo -DTSTART:20130711T050000Z -DTEND:20130711T053000Z -RRULE:FREQ=DAILY;INTERVAL=1;COUNT=2 -END:VEVENT -BEGIN:VEVENT -UID:foo -DTSTART:20130719T050000Z -DTEND:20130719T053000Z -RECURRENCE-ID:20130712T050000Z -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($input); - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCalendar', $vcal); - - $vcal->expand(new DateTime('2011-01-01'), new DateTime('2014-01-01')); - - $result = $vcal->serialize(); - - $output = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foo -DTSTART:20130711T050000Z -DTEND:20130711T053000Z -END:VEVENT -BEGIN:VEVENT -UID:foo -DTSTART:20130719T050000Z -DTEND:20130719T053000Z -RECURRENCE-ID:20130712T050000Z -END:VEVENT -END:VCALENDAR - -ICS; - $this->assertEquals($output, str_replace("\r", "", $result)); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/InfiniteLoopProblemTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,99 +0,0 @@ -<?php - -namespace Sabre\VObject\Recur\EventIterator; - -use - DateTime, - DateTimeZone, - Sabre\VObject\Component\VCalendar, - Sabre\VObject\Recur; - -class EventIteratorInfiniteLoopProblemTest extends \PHPUnit_Framework_TestCase { - - public function setUp() { - - $this->vcal = new VCalendar(); - - } - - /** - * This bug came from a Fruux customer. This would result in a never-ending - * request. - */ - function testFastForwardTooFar() { - - $ev = $this->vcal->createComponent('VEVENT'); - $ev->UID = 'foobar'; - $ev->DTSTART = '20090420T180000Z'; - $ev->RRULE = 'FREQ=WEEKLY;BYDAY=MO;UNTIL=20090704T205959Z;INTERVAL=1'; - - $this->assertFalse($ev->isInTimeRange(new DateTime('2012-01-01 12:00:00'),new DateTime('3000-01-01 00:00:00'))); - - } - - /** - * Different bug, also likely an infinite loop. - */ - function testYearlyByMonthLoop() { - - $ev = $this->vcal->createComponent('VEVENT'); - $ev->UID = 'uuid'; - $ev->DTSTART = '20120101T154500'; - $ev->DTSTART['TZID'] = 'Europe/Berlin'; - $ev->RRULE = 'FREQ=YEARLY;INTERVAL=1;UNTIL=20120203T225959Z;BYMONTH=2;BYSETPOS=1;BYDAY=SU,MO,TU,WE,TH,FR,SA'; - $ev->DTEND = '20120101T164500'; - $ev->DTEND['TZID'] = 'Europe/Berlin'; - - // This recurrence rule by itself is a yearly rule that should happen - // every february. - // - // The BYDAY part expands this to every day of the month, but the - // BYSETPOS limits this to only the 1st day of the month. Very crazy - // way to specify this, and could have certainly been a lot easier. - $this->vcal->add($ev); - - $it = new Recur\EventIterator($this->vcal,'uuid'); - $it->fastForward(new DateTime('2012-01-29 23:00:00', new DateTimeZone('UTC'))); - - $collect = array(); - - while($it->valid()) { - $collect[] = $it->getDTSTART(); - if ($it->getDTSTART() > new DateTime('2013-02-05 22:59:59', new DateTimeZone('UTC'))) { - break; - } - $it->next(); - - } - - $this->assertEquals( - array(new DateTime('2012-02-01 15:45:00', new DateTimeZone('Europe/Berlin'))), - $collect - ); - - } - - /** - * Something, somewhere produced an ics with an interval set to 0. Because - * this means we increase the current day (or week, month) by 0, this also - * results in an infinite loop. - * - * @expectedException InvalidArgumentException - * @return void - */ - function testZeroInterval() { - - $ev = $this->vcal->createComponent('VEVENT'); - $ev->UID = 'uuid'; - $ev->DTSTART = '20120824T145700Z'; - $ev->RRULE = 'FREQ=YEARLY;INTERVAL=0'; - $this->vcal->add($ev); - - $it = new Recur\EventIterator($this->vcal,'uuid'); - $it->fastForward(new DateTime('2013-01-01 23:00:00', new DateTimeZone('UTC'))); - - // if we got this far.. it means we are no longer infinitely looping - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/Issue48Test.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,49 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - DateTime, - DateTimeZone; - -class Issue48Test extends \PHPUnit_Framework_TestCase { - - function testExpand() { - - $input = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foo -DTEND;TZID=Europe/Moscow:20130710T120000 -DTSTART;TZID=Europe/Moscow:20130710T110000 -RRULE:FREQ=DAILY;UNTIL=20130712T195959Z -END:VEVENT -BEGIN:VEVENT -UID:foo -DTEND;TZID=Europe/Moscow:20130713T120000 -DTSTART;TZID=Europe/Moscow:20130713T110000 -RECURRENCE-ID;TZID=Europe/Moscow:20130711T110000 -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($input); - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCalendar', $vcal); - - $it = new Recur\EventIterator($vcal, 'foo'); - - $result = iterator_to_array($it); - - $tz = new DateTimeZone('Europe/Moscow'); - - $expected = array( - new DateTime('2013-07-10 11:00:00', $tz), - new DateTime('2013-07-12 11:00:00', $tz), - new DateTime('2013-07-13 11:00:00', $tz), - ); - - $this->assertEquals($expected, $result); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/Issue50Test.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,128 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - DateTime, - DateTimeZone; - -class Issue50Test extends \PHPUnit_Framework_TestCase { - - function testExpand() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Mozilla.org/NONSGML Mozilla Calendar V1.1//EN -BEGIN:VTIMEZONE -TZID:Europe/Brussels -X-LIC-LOCATION:Europe/Brussels -BEGIN:DAYLIGHT -TZOFFSETFROM:+0100 -TZOFFSETTO:+0200 -TZNAME:CEST -DTSTART:19700329T020000 -RRULE:FREQ=YEARLY;BYDAY=-1SU;BYMONTH=3 -END:DAYLIGHT -BEGIN:STANDARD -TZOFFSETFROM:+0200 -TZOFFSETTO:+0100 -TZNAME:CET -DTSTART:19701025T030000 -RRULE:FREQ=YEARLY;BYDAY=-1SU;BYMONTH=10 -END:STANDARD -END:VTIMEZONE -BEGIN:VEVENT -CREATED:20130705T142510Z -LAST-MODIFIED:20130715T132556Z -DTSTAMP:20130715T132556Z -UID:1aef0b27-3d92-4581-829a-11999dd36724 -SUMMARY:Werken -RRULE:FREQ=DAILY;COUNT=5 -DTSTART;TZID=Europe/Brussels:20130715T090000 -DTEND;TZID=Europe/Brussels:20130715T170000 -LOCATION:Job -DESCRIPTION:Vrij -X-MOZ-GENERATION:9 -END:VEVENT -BEGIN:VEVENT -CREATED:20130715T081654Z -LAST-MODIFIED:20130715T110931Z -DTSTAMP:20130715T110931Z -UID:1aef0b27-3d92-4581-829a-11999dd36724 -SUMMARY:Werken -RECURRENCE-ID;TZID=Europe/Brussels:20130719T090000 -DTSTART;TZID=Europe/Brussels:20130719T070000 -DTEND;TZID=Europe/Brussels:20130719T150000 -SEQUENCE:1 -LOCATION:Job -DESCRIPTION:Vrij -X-MOZ-GENERATION:1 -END:VEVENT -BEGIN:VEVENT -CREATED:20130715T111654Z -LAST-MODIFIED:20130715T132556Z -DTSTAMP:20130715T132556Z -UID:1aef0b27-3d92-4581-829a-11999dd36724 -SUMMARY:Werken -RECURRENCE-ID;TZID=Europe/Brussels:20130716T090000 -DTSTART;TZID=Europe/Brussels:20130716T070000 -DTEND;TZID=Europe/Brussels:20130716T150000 -SEQUENCE:1 -LOCATION:Job -X-MOZ-GENERATION:2 -END:VEVENT -BEGIN:VEVENT -CREATED:20130715T125942Z -LAST-MODIFIED:20130715T130023Z -DTSTAMP:20130715T130023Z -UID:1aef0b27-3d92-4581-829a-11999dd36724 -SUMMARY:Werken -RECURRENCE-ID;TZID=Europe/Brussels:20130717T090000 -DTSTART;TZID=Europe/Brussels:20130717T070000 -DTEND;TZID=Europe/Brussels:20130717T150000 -SEQUENCE:1 -LOCATION:Job -X-MOZ-GENERATION:3 -END:VEVENT -BEGIN:VEVENT -CREATED:20130715T130024Z -LAST-MODIFIED:20130715T130034Z -DTSTAMP:20130715T130034Z -UID:1aef0b27-3d92-4581-829a-11999dd36724 -SUMMARY:Werken -RECURRENCE-ID;TZID=Europe/Brussels:20130718T090000 -DTSTART;TZID=Europe/Brussels:20130718T090000 -DTEND;TZID=Europe/Brussels:20130718T170000 -LOCATION:Job -X-MOZ-GENERATION:5 -DESCRIPTION:Vrij -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($input); - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCalendar', $vcal); - - $it = new Recur\EventIterator($vcal, '1aef0b27-3d92-4581-829a-11999dd36724'); - - $result = array(); - foreach($it as $instance) { - - $result[] = $instance; - - } - - $tz = new DateTimeZone('Europe/Brussels'); - - $this->assertEquals(array( - new DateTime('2013-07-15 09:00:00', $tz), - new DateTime('2013-07-16 07:00:00', $tz), - new DateTime('2013-07-17 07:00:00', $tz), - new DateTime('2013-07-18 09:00:00', $tz), - new DateTime('2013-07-19 07:00:00', $tz), - ), $result); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/MainTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1427 +0,0 @@ -<?php - -namespace Sabre\VObject\EventIterator; - -use DateTime; -use DateTimeZone; -use Sabre\VObject\Recur\EventIterator; -use Sabre\VObject\Component\VCalendar; - -class MainTest extends \PHPUnit_Framework_TestCase { - - function testValues() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=DAILY;BYHOUR=10;BYMINUTE=5;BYSECOND=16;BYWEEKNO=32;BYYEARDAY=100,200'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07')); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $this->assertTrue($it->isInfinite()); - - } - - /** - * @expectedException InvalidArgumentException - * @depends testValues - */ - function testInvalidFreq() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - $ev->RRULE = 'FREQ=SMONTHLY;INTERVAL=3;UNTIL=20111025T000000Z'; - $ev->UID = 'foo'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testVCalendarNoUID() { - - $vcal = new VCalendar(); - $it = new EventIterator($vcal); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testVCalendarInvalidUID() { - - $vcal = new VCalendar(); - $it = new EventIterator($vcal,'foo'); - - } - - /** - * @depends testValues - */ - function testHourly() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=HOURLY;INTERVAL=3;UNTIL=20111025T000000Z'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07 12:00:00', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - $vcal->add($ev); - - $it = new EventIterator($vcal,$ev->uid); - - // Max is to prevent overflow - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-10-07 12:00:00', $tz), - new DateTime('2011-10-07 15:00:00', $tz), - new DateTime('2011-10-07 18:00:00', $tz), - new DateTime('2011-10-07 21:00:00', $tz), - new DateTime('2011-10-08 00:00:00', $tz), - new DateTime('2011-10-08 03:00:00', $tz), - new DateTime('2011-10-08 06:00:00', $tz), - new DateTime('2011-10-08 09:00:00', $tz), - new DateTime('2011-10-08 12:00:00', $tz), - new DateTime('2011-10-08 15:00:00', $tz), - new DateTime('2011-10-08 18:00:00', $tz), - new DateTime('2011-10-08 21:00:00', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testDaily() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=DAILY;INTERVAL=3;UNTIL=20111025T000000Z'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,$ev->uid); - - // Max is to prevent overflow - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-10-07', $tz), - new DateTime('2011-10-10', $tz), - new DateTime('2011-10-13', $tz), - new DateTime('2011-10-16', $tz), - new DateTime('2011-10-19', $tz), - new DateTime('2011-10-22', $tz), - new DateTime('2011-10-25', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testNoRRULE() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,$ev->uid); - - // Max is to prevent overflow - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-10-07', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testDailyByDayByHour() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=DAILY;BYDAY=SA,SU;BYHOUR=6,7'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-08 06:00:00', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - // Grabbing the next 12 items - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new datetime('2011-10-08 06:00:00', $tz), - new datetime('2011-10-08 07:00:00', $tz), - new datetime('2011-10-09 06:00:00', $tz), - new datetime('2011-10-09 07:00:00', $tz), - new datetime('2011-10-15 06:00:00', $tz), - new datetime('2011-10-15 07:00:00', $tz), - new datetime('2011-10-16 06:00:00', $tz), - new datetime('2011-10-16 07:00:00', $tz), - new datetime('2011-10-22 06:00:00', $tz), - new datetime('2011-10-22 07:00:00', $tz), - new datetime('2011-10-23 06:00:00', $tz), - new datetime('2011-10-23 07:00:00', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testDailyByHour() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=DAILY;INTERVAL=2;BYHOUR=10,11,12,13,14,15'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2012-10-11 12:00:00', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - // Grabbing the next 12 items - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new datetime('2012-10-11 12:00:00', $tz), - new datetime('2012-10-11 13:00:00', $tz), - new datetime('2012-10-11 14:00:00', $tz), - new datetime('2012-10-11 15:00:00', $tz), - new datetime('2012-10-13 10:00:00', $tz), - new datetime('2012-10-13 11:00:00', $tz), - new datetime('2012-10-13 12:00:00', $tz), - new datetime('2012-10-13 13:00:00', $tz), - new datetime('2012-10-13 14:00:00', $tz), - new datetime('2012-10-13 15:00:00', $tz), - new datetime('2012-10-15 10:00:00', $tz), - new datetime('2012-10-15 11:00:00', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testDailyByDay() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=DAILY;INTERVAL=2;BYDAY=TU,WE,FR'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - // Grabbing the next 12 items - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-10-07', $tz), - new DateTime('2011-10-11', $tz), - new DateTime('2011-10-19', $tz), - new DateTime('2011-10-21', $tz), - new DateTime('2011-10-25', $tz), - new DateTime('2011-11-02', $tz), - new DateTime('2011-11-04', $tz), - new DateTime('2011-11-08', $tz), - new DateTime('2011-11-16', $tz), - new DateTime('2011-11-18', $tz), - new DateTime('2011-11-22', $tz), - new DateTime('2011-11-30', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testWeekly() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=WEEKLY;INTERVAL=2;COUNT=10'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - // Max is to prevent overflow - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-10-07', $tz), - new DateTime('2011-10-21', $tz), - new DateTime('2011-11-04', $tz), - new DateTime('2011-11-18', $tz), - new DateTime('2011-12-02', $tz), - new DateTime('2011-12-16', $tz), - new DateTime('2011-12-30', $tz), - new DateTime('2012-01-13', $tz), - new DateTime('2012-01-27', $tz), - new DateTime('2012-02-10', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testWeeklyByDayByHour() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=WEEKLY;INTERVAL=2;BYDAY=TU,WE,FR;WKST=MO;BYHOUR=8,9,10'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07 08:00:00', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - // Grabbing the next 12 items - $max = 15; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-10-07 08:00:00', $tz), - new DateTime('2011-10-07 09:00:00', $tz), - new DateTime('2011-10-07 10:00:00', $tz), - new DateTime('2011-10-18 08:00:00', $tz), - new DateTime('2011-10-18 09:00:00', $tz), - new DateTime('2011-10-18 10:00:00', $tz), - new DateTime('2011-10-19 08:00:00', $tz), - new DateTime('2011-10-19 09:00:00', $tz), - new DateTime('2011-10-19 10:00:00', $tz), - new DateTime('2011-10-21 08:00:00', $tz), - new DateTime('2011-10-21 09:00:00', $tz), - new DateTime('2011-10-21 10:00:00', $tz), - new DateTime('2011-11-01 08:00:00', $tz), - new DateTime('2011-11-01 09:00:00', $tz), - new DateTime('2011-11-01 10:00:00', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testWeeklyByDaySpecificHour() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=WEEKLY;INTERVAL=2;BYDAY=TU,WE,FR;WKST=SU'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07 18:00:00', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - // Grabbing the next 12 items - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-10-07 18:00:00', $tz), - new DateTime('2011-10-18 18:00:00', $tz), - new DateTime('2011-10-19 18:00:00', $tz), - new DateTime('2011-10-21 18:00:00', $tz), - new DateTime('2011-11-01 18:00:00', $tz), - new DateTime('2011-11-02 18:00:00', $tz), - new DateTime('2011-11-04 18:00:00', $tz), - new DateTime('2011-11-15 18:00:00', $tz), - new DateTime('2011-11-16 18:00:00', $tz), - new DateTime('2011-11-18 18:00:00', $tz), - new DateTime('2011-11-29 18:00:00', $tz), - new DateTime('2011-11-30 18:00:00', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testWeeklyByDay() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=WEEKLY;INTERVAL=2;BYDAY=TU,WE,FR;WKST=SU'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - // Grabbing the next 12 items - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-10-07', $tz), - new DateTime('2011-10-18', $tz), - new DateTime('2011-10-19', $tz), - new DateTime('2011-10-21', $tz), - new DateTime('2011-11-01', $tz), - new DateTime('2011-11-02', $tz), - new DateTime('2011-11-04', $tz), - new DateTime('2011-11-15', $tz), - new DateTime('2011-11-16', $tz), - new DateTime('2011-11-18', $tz), - new DateTime('2011-11-29', $tz), - new DateTime('2011-11-30', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testMonthly() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=MONTHLY;INTERVAL=3;COUNT=5'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-12-05', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 14; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-12-05', $tz), - new DateTime('2012-03-05', $tz), - new DateTime('2012-06-05', $tz), - new DateTime('2012-09-05', $tz), - new DateTime('2012-12-05', $tz), - ), - $result - ); - - - } - - /** - * @depends testValues - */ - function testMonthlyEndOfMonth() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=MONTHLY;INTERVAL=2;COUNT=12'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-12-31', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 14; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-12-31', $tz), - new DateTime('2012-08-31', $tz), - new DateTime('2012-10-31', $tz), - new DateTime('2012-12-31', $tz), - new DateTime('2013-08-31', $tz), - new DateTime('2013-10-31', $tz), - new DateTime('2013-12-31', $tz), - new DateTime('2014-08-31', $tz), - new DateTime('2014-10-31', $tz), - new DateTime('2014-12-31', $tz), - new DateTime('2015-08-31', $tz), - new DateTime('2015-10-31', $tz), - ), - $result - ); - - - } - - /** - * @depends testValues - */ - function testMonthlyByMonthDay() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=MONTHLY;INTERVAL=5;COUNT=9;BYMONTHDAY=1,31,-7'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-01-01', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 14; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-01-01', $tz), - new DateTime('2011-01-25', $tz), - new DateTime('2011-01-31', $tz), - new DateTime('2011-06-01', $tz), - new DateTime('2011-06-24', $tz), - new DateTime('2011-11-01', $tz), - new DateTime('2011-11-24', $tz), - new DateTime('2012-04-01', $tz), - new DateTime('2012-04-24', $tz), - ), - $result - ); - - } - - /** - * A pretty slow test. Had to be marked as 'medium' for phpunit to not die - * after 1 second. Would be good to optimize later. - * - * @depends testValues - * @medium - */ - function testMonthlyByDay() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=MONTHLY;INTERVAL=2;COUNT=16;BYDAY=MO,-2TU,+1WE,3TH'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-01-03', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 20; - $result = array(); - foreach($it as $k=>$item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-01-03', $tz), - new DateTime('2011-01-05', $tz), - new DateTime('2011-01-10', $tz), - new DateTime('2011-01-17', $tz), - new DateTime('2011-01-18', $tz), - new DateTime('2011-01-20', $tz), - new DateTime('2011-01-24', $tz), - new DateTime('2011-01-31', $tz), - new DateTime('2011-03-02', $tz), - new DateTime('2011-03-07', $tz), - new DateTime('2011-03-14', $tz), - new DateTime('2011-03-17', $tz), - new DateTime('2011-03-21', $tz), - new DateTime('2011-03-22', $tz), - new DateTime('2011-03-28', $tz), - new DateTime('2011-05-02', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testMonthlyByDayByMonthDay() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=MONTHLY;COUNT=10;BYDAY=MO;BYMONTHDAY=1'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-08-01', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 20; - $result = array(); - foreach($it as $k=>$item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-08-01', $tz), - new DateTime('2012-10-01', $tz), - new DateTime('2013-04-01', $tz), - new DateTime('2013-07-01', $tz), - new DateTime('2014-09-01', $tz), - new DateTime('2014-12-01', $tz), - new DateTime('2015-06-01', $tz), - new DateTime('2016-02-01', $tz), - new DateTime('2016-08-01', $tz), - new DateTime('2017-05-01', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testMonthlyByDayBySetPos() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=MONTHLY;COUNT=10;BYDAY=MO,TU,WE,TH,FR;BYSETPOS=1,-1'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-01-03', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 20; - $result = array(); - foreach($it as $k=>$item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-01-03', $tz), - new DateTime('2011-01-31', $tz), - new DateTime('2011-02-01', $tz), - new DateTime('2011-02-28', $tz), - new DateTime('2011-03-01', $tz), - new DateTime('2011-03-31', $tz), - new DateTime('2011-04-01', $tz), - new DateTime('2011-04-29', $tz), - new DateTime('2011-05-02', $tz), - new DateTime('2011-05-31', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testYearly() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=YEARLY;COUNT=10;INTERVAL=3'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-01-01', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 20; - $result = array(); - foreach($it as $k=>$item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-01-01', $tz), - new DateTime('2014-01-01', $tz), - new DateTime('2017-01-01', $tz), - new DateTime('2020-01-01', $tz), - new DateTime('2023-01-01', $tz), - new DateTime('2026-01-01', $tz), - new DateTime('2029-01-01', $tz), - new DateTime('2032-01-01', $tz), - new DateTime('2035-01-01', $tz), - new DateTime('2038-01-01', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testYearlyLeapYear() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=YEARLY;COUNT=3'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2012-02-29', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 20; - $result = array(); - foreach($it as $k=>$item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2012-02-29', $tz), - new DateTime('2016-02-29', $tz), - new DateTime('2020-02-29', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testYearlyByMonth() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=YEARLY;COUNT=8;INTERVAL=4;BYMONTH=4,10'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-04-07', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 20; - $result = array(); - foreach($it as $k=>$item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-04-07', $tz), - new DateTime('2011-10-07', $tz), - new DateTime('2015-04-07', $tz), - new DateTime('2015-10-07', $tz), - new DateTime('2019-04-07', $tz), - new DateTime('2019-10-07', $tz), - new DateTime('2023-04-07', $tz), - new DateTime('2023-10-07', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testYearlyByMonthByDay() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=YEARLY;COUNT=8;INTERVAL=5;BYMONTH=4,10;BYDAY=1MO,-1SU'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-04-04', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 20; - $result = array(); - foreach($it as $k=>$item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-04-04', $tz), - new DateTime('2011-04-24', $tz), - new DateTime('2011-10-03', $tz), - new DateTime('2011-10-30', $tz), - new DateTime('2016-04-04', $tz), - new DateTime('2016-04-24', $tz), - new DateTime('2016-10-03', $tz), - new DateTime('2016-10-30', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testFastForward() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=YEARLY;COUNT=8;INTERVAL=5;BYMONTH=4,10;BYDAY=1MO,-1SU'; - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-04-04', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - // The idea is that we're fast-forwarding too far in the future, so - // there will be no results left. - $it->fastForward(new DateTime('2020-05-05', new DateTimeZone('UTC'))); - - $max = 20; - $result = array(); - while($item = $it->current()) { - - $result[] = $item; - $max--; - - if (!$max) break; - $it->next(); - - } - - $tz = new DateTimeZone('UTC'); - $this->assertEquals(array(), $result); - - } - - /** - * @depends testValues - */ - function testComplexExclusions() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RRULE = 'FREQ=YEARLY;COUNT=10'; - $dtStart = $vcal->createProperty('DTSTART'); - - $tz = new DateTimeZone('Canada/Eastern'); - $dtStart->setDateTime(new DateTime('2011-01-01 13:50:20', $tz)); - - $exDate1 = $vcal->createProperty('EXDATE'); - $exDate1->setDateTimes(array(new DateTime('2012-01-01 13:50:20', $tz), new DateTime('2014-01-01 13:50:20', $tz))); - $exDate2 = $vcal->createProperty('EXDATE'); - $exDate2->setDateTimes(array(new DateTime('2016-01-01 13:50:20', $tz))); - - $ev->add($dtStart); - $ev->add($exDate1); - $ev->add($exDate2); - - $vcal->add($ev); - - $it = new EventIterator($vcal,(string)$ev->uid); - - $max = 20; - $result = array(); - foreach($it as $k=>$item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $this->assertEquals( - array( - new DateTime('2011-01-01 13:50:20', $tz), - new DateTime('2013-01-01 13:50:20', $tz), - new DateTime('2015-01-01 13:50:20', $tz), - new DateTime('2017-01-01 13:50:20', $tz), - new DateTime('2018-01-01 13:50:20', $tz), - new DateTime('2019-01-01 13:50:20', $tz), - new DateTime('2020-01-01 13:50:20', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - */ - function testOverridenEvent() { - - $vcal = new VCalendar(); - - $ev1 = $vcal->createComponent('VEVENT'); - $ev1->UID = 'overridden'; - $ev1->RRULE = 'FREQ=DAILY;COUNT=10'; - $ev1->DTSTART = '20120107T120000Z'; - $ev1->SUMMARY = 'baseEvent'; - - $vcal->add($ev1); - - // ev2 overrides an event, and puts it on 2pm instead. - $ev2 = $vcal->createComponent('VEVENT'); - $ev2->UID = 'overridden'; - $ev2->{'RECURRENCE-ID'} = '20120110T120000Z'; - $ev2->DTSTART = '20120110T140000Z'; - $ev2->SUMMARY = 'Event 2'; - - $vcal->add($ev2); - - // ev3 overrides an event, and puts it 2 days and 2 hours later - $ev3 = $vcal->createComponent('VEVENT'); - $ev3->UID = 'overridden'; - $ev3->{'RECURRENCE-ID'} = '20120113T120000Z'; - $ev3->DTSTART = '20120115T140000Z'; - $ev3->SUMMARY = 'Event 3'; - - $vcal->add($ev3); - - $it = new EventIterator($vcal,'overridden'); - - $dates = array(); - $summaries = array(); - while($it->valid()) { - - $dates[] = $it->getDTStart(); - $summaries[] = (string)$it->getEventObject()->SUMMARY; - $it->next(); - - } - - $tz = new DateTimeZone('UTC'); - $this->assertEquals(array( - new DateTime('2012-01-07 12:00:00',$tz), - new DateTime('2012-01-08 12:00:00',$tz), - new DateTime('2012-01-09 12:00:00',$tz), - new DateTime('2012-01-10 14:00:00',$tz), - new DateTime('2012-01-11 12:00:00',$tz), - new DateTime('2012-01-12 12:00:00',$tz), - new DateTime('2012-01-14 12:00:00',$tz), - new DateTime('2012-01-15 12:00:00',$tz), - new DateTime('2012-01-15 14:00:00',$tz), - new DateTime('2012-01-16 12:00:00',$tz), - ), $dates); - - $this->assertEquals(array( - 'baseEvent', - 'baseEvent', - 'baseEvent', - 'Event 2', - 'baseEvent', - 'baseEvent', - 'baseEvent', - 'baseEvent', - 'Event 3', - 'baseEvent', - ), $summaries); - - } - - /** - * @depends testValues - */ - function testOverridenEvent2() { - - $vcal = new VCalendar(); - - $ev1 = $vcal->createComponent('VEVENT'); - $ev1->UID = 'overridden'; - $ev1->RRULE = 'FREQ=WEEKLY;COUNT=3'; - $ev1->DTSTART = '20120112T120000Z'; - $ev1->SUMMARY = 'baseEvent'; - - $vcal->add($ev1); - - // ev2 overrides an event, and puts it 6 days earlier instead. - $ev2 = $vcal->createComponent('VEVENT'); - $ev2->UID = 'overridden'; - $ev2->{'RECURRENCE-ID'} = '20120119T120000Z'; - $ev2->DTSTART = '20120113T120000Z'; - $ev2->SUMMARY = 'Override!'; - - $vcal->add($ev2); - - $it = new EventIterator($vcal,'overridden'); - - $dates = array(); - $summaries = array(); - while($it->valid()) { - - $dates[] = $it->getDTStart(); - $summaries[] = (string)$it->getEventObject()->SUMMARY; - $it->next(); - - } - - $tz = new DateTimeZone('UTC'); - $this->assertEquals(array( - new DateTime('2012-01-12 12:00:00',$tz), - new DateTime('2012-01-13 12:00:00',$tz), - new DateTime('2012-01-26 12:00:00',$tz), - - ), $dates); - - $this->assertEquals(array( - 'baseEvent', - 'Override!', - 'baseEvent', - ), $summaries); - - } - - /** - * @depends testValues - */ - function testOverridenEventNoValuesExpected() { - - $vcal = new VCalendar(); - $ev1 = $vcal->createComponent('VEVENT'); - - $ev1->UID = 'overridden'; - $ev1->RRULE = 'FREQ=WEEKLY;COUNT=3'; - $ev1->DTSTART = '20120124T120000Z'; - $ev1->SUMMARY = 'baseEvent'; - - $vcal->add($ev1); - - // ev2 overrides an event, and puts it 6 days earlier instead. - $ev2 = $vcal->createComponent('VEVENT'); - $ev2->UID = 'overridden'; - $ev2->{'RECURRENCE-ID'} = '20120131T120000Z'; - $ev2->DTSTART = '20120125T120000Z'; - $ev2->SUMMARY = 'Override!'; - - $vcal->add($ev2); - - $it = new EventIterator($vcal,'overridden'); - - $dates = array(); - $summaries = array(); - - // The reported problem was specifically related to the VCALENDAR - // expansion. In this parcitular case, we had to forward to the 28th of - // january. - $it->fastForward(new DateTime('2012-01-28 23:00:00')); - - // We stop the loop when it hits the 6th of februari. Normally this - // iterator would hit 24, 25 (overriden from 31) and 7 feb but because - // we 'filter' from the 28th till the 6th, we should get 0 results. - while($it->valid() && $it->getDTSTart() < new DateTime('2012-02-06 23:00:00')) { - - $dates[] = $it->getDTStart(); - $summaries[] = (string)$it->getEventObject()->SUMMARY; - $it->next(); - - } - - $this->assertEquals(array(), $dates); - $this->assertEquals(array(), $summaries); - - } - - /** - * @depends testValues - */ - function testRDATE() { - - $vcal = new VCalendar(); - $ev = $vcal->createComponent('VEVENT'); - - $ev->UID = 'bla'; - $ev->RDATE = array( - new DateTime('2014-08-07', new DateTimeZone('UTC')), - new DateTime('2014-08-08', new DateTimeZone('UTC')), - ); - $dtStart = $vcal->createProperty('DTSTART'); - $dtStart->setDateTime(new DateTime('2011-10-07', new DateTimeZone('UTC'))); - - $ev->add($dtStart); - - $vcal->add($ev); - - $it = new EventIterator($vcal,$ev->uid); - - // Max is to prevent overflow - $max = 12; - $result = array(); - foreach($it as $item) { - - $result[] = $item; - $max--; - - if (!$max) break; - - } - - $tz = new DateTimeZone('UTC'); - - $this->assertEquals( - array( - new DateTime('2011-10-07', $tz), - new DateTime('2014-08-07', $tz), - new DateTime('2014-08-08', $tz), - ), - $result - ); - - } - - /** - * @depends testValues - * @expectedException \InvalidArgumentException - */ - function testNoMasterBadUID() { - - $vcal = new VCalendar(); - // ev2 overrides an event, and puts it on 2pm instead. - $ev2 = $vcal->createComponent('VEVENT'); - $ev2->UID = 'overridden'; - $ev2->{'RECURRENCE-ID'} = '20120110T120000Z'; - $ev2->DTSTART = '20120110T140000Z'; - $ev2->SUMMARY = 'Event 2'; - - $vcal->add($ev2); - - // ev3 overrides an event, and puts it 2 days and 2 hours later - $ev3 = $vcal->createComponent('VEVENT'); - $ev3->UID = 'overridden'; - $ev3->{'RECURRENCE-ID'} = '20120113T120000Z'; - $ev3->DTSTART = '20120115T140000Z'; - $ev3->SUMMARY = 'Event 3'; - - $vcal->add($ev3); - - $it = new EventIterator($vcal,'broken'); - - } -} -
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/MissingOverriddenTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,63 +0,0 @@ -<?php - -namespace Sabre\VObject; - -use - DateTime, - DateTimeZone; - -class RecurrenceIteratorMissingOverriddenTest extends \PHPUnit_Framework_TestCase { - - function testExpand() { - - $input = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foo -DTSTART:20130727T120000Z -DURATION:PT1H -RRULE:FREQ=DAILY;COUNT=2 -SUMMARY:A -END:VEVENT -BEGIN:VEVENT -RECURRENCE-ID:20130728T120000Z -UID:foo -DTSTART:20140101T120000Z -DURATION:PT1H -SUMMARY:B -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($input); - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCalendar', $vcal); - - $vcal->expand(new DateTime('2011-01-01'), new DateTime('2015-01-01')); - - $result = $vcal->serialize(); - - $output = <<<ICS -BEGIN:VCALENDAR -VERSION:2.0 -BEGIN:VEVENT -UID:foo -DTSTART:20130727T120000Z -DURATION:PT1H -SUMMARY:A -END:VEVENT -BEGIN:VEVENT -RECURRENCE-ID:20130728T120000Z -UID:foo -DTSTART:20140101T120000Z -DURATION:PT1H -SUMMARY:B -END:VEVENT -END:VCALENDAR - -ICS; - $this->assertEquals($output, str_replace("\r","",$result)); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/NoInstancesTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,40 +0,0 @@ -<?php - -namespace Sabre\VObject\Recur; - -use - Sabre\VObject\Reader; - -class IssueEXDATETest extends \PHPUnit_Framework_TestCase { - - /** - * @expectedException \Sabre\VObject\Recur\NoInstancesException - */ - function testRecurrence() { - - $input = <<<ICS -BEGIN:VCALENDAR -PRODID:-//Google Inc//Google Calendar 70.9054//EN -VERSION:2.0 -BEGIN:VEVENT -DTSTART;TZID=Europe/Berlin:20130329T140000 -DTEND;TZID=Europe/Berlin:20130329T153000 -RRULE:FREQ=WEEKLY;BYDAY=FR;UNTIL=20130412T115959Z -EXDATE;TZID=Europe/Berlin:20130405T140000 -EXDATE;TZID=Europe/Berlin:20130329T140000 -DTSTAMP:20140916T201215Z -UID:foo -SEQUENCE:1 -SUMMARY:foo -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($input); - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCalendar', $vcal); - - $it = new EventIterator($vcal, 'foo'); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/EventIterator/OverrideFirstEventTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,122 +0,0 @@ -<?php - -namespace Sabre\VObject\RecurrenceIterator; - -use Sabre\VObject\Reader; -use DateTime; - -class OverrideFirstEventTest extends \PHPUnit_Framework_TestCase { - - function testOverrideFirstEvent() { - - $input = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART:20140803T120000Z -RRULE:FREQ=WEEKLY -SUMMARY:Original -END:VEVENT -BEGIN:VEVENT -UID:foobar -RECURRENCE-ID:20140803T120000Z -DTSTART:20140803T120000Z -SUMMARY:Overridden -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($input); - $vcal->expand(new DateTime('2014-08-01'), new DateTime('2014-09-01')); - - $expected = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -RECURRENCE-ID:20140803T120000Z -DTSTART:20140803T120000Z -SUMMARY:Overridden -END:VEVENT -BEGIN:VEVENT -UID:foobar -DTSTART:20140810T120000Z -SUMMARY:Original -RECURRENCE-ID:20140810T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -DTSTART:20140817T120000Z -SUMMARY:Original -RECURRENCE-ID:20140817T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -DTSTART:20140824T120000Z -SUMMARY:Original -RECURRENCE-ID:20140824T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -DTSTART:20140831T120000Z -SUMMARY:Original -RECURRENCE-ID:20140831T120000Z -END:VEVENT -END:VCALENDAR - -ICS; - - $newIcs = $vcal->serialize(); - $newIcs = str_replace("\r\n","\n", $newIcs); - $this->assertEquals( - $expected, - $newIcs - ); - - - } - - function testRemoveFirstEvent() { - - $input = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART:20140803T120000Z -RRULE:FREQ=WEEKLY -EXDATE:20140803T120000Z -SUMMARY:Original -END:VEVENT -END:VCALENDAR -ICS; - - $vcal = Reader::read($input); - $vcal->expand(new DateTime('2014-08-01'), new DateTime('2014-08-19')); - - $expected = <<<ICS -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foobar -DTSTART:20140810T120000Z -SUMMARY:Original -RECURRENCE-ID:20140810T120000Z -END:VEVENT -BEGIN:VEVENT -UID:foobar -DTSTART:20140817T120000Z -SUMMARY:Original -RECURRENCE-ID:20140817T120000Z -END:VEVENT -END:VCALENDAR - -ICS; - - $newIcs = $vcal->serialize(); - $newIcs = str_replace("\r\n","\n", $newIcs); - $this->assertEquals( - $expected, - $newIcs - ); - - - } -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/RDateIteratorTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,56 +0,0 @@ -<?php - -namespace Sabre\VObject\Recur; - -use DateTime; -use DateTimeZone; - -class RDateIteratorTest extends \PHPUnit_Framework_TestCase { - - function testSimple() { - - $utc = new DateTimeZone('UTC'); - $it = new RDateIterator('20140901T000000Z,20141001T000000Z', new DateTime('2014-08-01 00:00:00', $utc)); - - $expected = array( - new DateTime('2014-08-01 00:00:00', $utc), - new DateTime('2014-09-01 00:00:00', $utc), - new DateTime('2014-10-01 00:00:00', $utc), - ); - - $this->assertEquals( - $expected, - iterator_to_array($it) - ); - - $this->assertFalse($it->isInfinite()); - - } - - function testFastForward() { - - $utc = new DateTimeZone('UTC'); - $it = new RDateIterator('20140901T000000Z,20141001T000000Z', new DateTime('2014-08-01 00:00:00', $utc)); - - $it->fastForward(new DateTime('2014-08-15 00:00:00')); - - $result = array(); - while($it->valid()) { - $result[] = $it->current(); - $it->next(); - } - - $expected = array( - new DateTime('2014-09-01 00:00:00', $utc), - new DateTime('2014-10-01 00:00:00', $utc), - ); - - $this->assertEquals( - $expected, - $result - ); - - $this->assertFalse($it->isInfinite()); - - } -}
--- a/vendor/sabre/vobject/tests/VObject/Recur/RRuleIteratorTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,698 +0,0 @@ -<?php - -namespace Sabre\VObject\Recur; - -use DateTime; -use DateTimeZone; - -class RRuleIteratorTest extends \PHPUnit_Framework_TestCase { - - function testHourly() { - - $this->parse( - 'FREQ=HOURLY;INTERVAL=3;COUNT=12', - '2011-10-07 12:00:00', - array( - '2011-10-07 12:00:00', - '2011-10-07 15:00:00', - '2011-10-07 18:00:00', - '2011-10-07 21:00:00', - '2011-10-08 00:00:00', - '2011-10-08 03:00:00', - '2011-10-08 06:00:00', - '2011-10-08 09:00:00', - '2011-10-08 12:00:00', - '2011-10-08 15:00:00', - '2011-10-08 18:00:00', - '2011-10-08 21:00:00', - ) - ); - - } - - function testDaily() { - - $this->parse( - 'FREQ=DAILY;INTERVAL=3;UNTIL=20111025T000000Z', - '2011-10-07', - array( - '2011-10-07 00:00:00', - '2011-10-10 00:00:00', - '2011-10-13 00:00:00', - '2011-10-16 00:00:00', - '2011-10-19 00:00:00', - '2011-10-22 00:00:00', - '2011-10-25 00:00:00', - ) - ); - - } - - function testDailyByDayByHour() { - - $this->parse( - 'FREQ=DAILY;BYDAY=SA,SU;BYHOUR=6,7', - '2011-10-08 06:00:00', - array( - '2011-10-08 06:00:00', - '2011-10-08 07:00:00', - '2011-10-09 06:00:00', - '2011-10-09 07:00:00', - '2011-10-15 06:00:00', - '2011-10-15 07:00:00', - '2011-10-16 06:00:00', - '2011-10-16 07:00:00', - '2011-10-22 06:00:00', - '2011-10-22 07:00:00', - '2011-10-23 06:00:00', - '2011-10-23 07:00:00', - ) - ); - - } - - function testDailyByHour() { - - $this->parse( - 'FREQ=DAILY;INTERVAL=2;BYHOUR=10,11,12,13,14,15', - '2012-10-11 12:00:00', - array( - '2012-10-11 12:00:00', - '2012-10-11 13:00:00', - '2012-10-11 14:00:00', - '2012-10-11 15:00:00', - '2012-10-13 10:00:00', - '2012-10-13 11:00:00', - '2012-10-13 12:00:00', - '2012-10-13 13:00:00', - '2012-10-13 14:00:00', - '2012-10-13 15:00:00', - '2012-10-15 10:00:00', - '2012-10-15 11:00:00', - ) - ); - - } - - function testDailyByDay() { - - $this->parse( - 'FREQ=DAILY;INTERVAL=2;BYDAY=TU,WE,FR', - '2011-10-07 12:00:00', - array( - '2011-10-07 12:00:00', - '2011-10-11 12:00:00', - '2011-10-19 12:00:00', - '2011-10-21 12:00:00', - '2011-10-25 12:00:00', - '2011-11-02 12:00:00', - '2011-11-04 12:00:00', - '2011-11-08 12:00:00', - '2011-11-16 12:00:00', - '2011-11-18 12:00:00', - '2011-11-22 12:00:00', - '2011-11-30 12:00:00', - ) - ); - - } - - function testDailyCount() { - - $this->parse( - 'FREQ=DAILY;COUNT=5', - '2014-08-01 18:03:00', - array( - '2014-08-01 18:03:00', - '2014-08-02 18:03:00', - '2014-08-03 18:03:00', - '2014-08-04 18:03:00', - '2014-08-05 18:03:00', - ) - ); - - } - - function testDailyByMonth() { - - $this->parse( - 'FREQ=DAILY;BYMONTH=9,10;BYDAY=SU', - '2007-10-04 16:00:00', - array( - "2013-09-29 16:00:00", - "2013-10-06 16:00:00", - "2013-10-13 16:00:00", - "2013-10-20 16:00:00", - "2013-10-27 16:00:00", - "2014-09-07 16:00:00" - ), - '2013-09-28' - ); - - } - - function testWeekly() { - - $this->parse( - 'FREQ=WEEKLY;INTERVAL=2;COUNT=10', - '2011-10-07 00:00:00', - array( - '2011-10-07 00:00:00', - '2011-10-21 00:00:00', - '2011-11-04 00:00:00', - '2011-11-18 00:00:00', - '2011-12-02 00:00:00', - '2011-12-16 00:00:00', - '2011-12-30 00:00:00', - '2012-01-13 00:00:00', - '2012-01-27 00:00:00', - '2012-02-10 00:00:00', - ) - ); - - } - - function testWeeklyByDay() { - - $this->parse( - 'FREQ=WEEKLY;INTERVAL=1;COUNT=4;BYDAY=MO;WKST=SA', - '2014-08-01 00:00:00', - array( - '2014-08-01 00:00:00', - '2014-08-04 00:00:00', - '2014-08-11 00:00:00', - '2014-08-18 00:00:00', - ) - ); - - } - - function testWeeklyByDay2() { - - $this->parse( - 'FREQ=WEEKLY;INTERVAL=2;BYDAY=TU,WE,FR;WKST=SU', - '2011-10-07 00:00:00', - array( - '2011-10-07 00:00:00', - '2011-10-18 00:00:00', - '2011-10-19 00:00:00', - '2011-10-21 00:00:00', - '2011-11-01 00:00:00', - '2011-11-02 00:00:00', - '2011-11-04 00:00:00', - '2011-11-15 00:00:00', - '2011-11-16 00:00:00', - '2011-11-18 00:00:00', - '2011-11-29 00:00:00', - '2011-11-30 00:00:00', - ) - ); - - } - - function testWeeklyByDayByHour() { - - $this->parse( - 'FREQ=WEEKLY;INTERVAL=2;BYDAY=TU,WE,FR;WKST=MO;BYHOUR=8,9,10', - '2011-10-07 08:00:00', - array( - '2011-10-07 08:00:00', - '2011-10-07 09:00:00', - '2011-10-07 10:00:00', - '2011-10-18 08:00:00', - '2011-10-18 09:00:00', - '2011-10-18 10:00:00', - '2011-10-19 08:00:00', - '2011-10-19 09:00:00', - '2011-10-19 10:00:00', - '2011-10-21 08:00:00', - '2011-10-21 09:00:00', - '2011-10-21 10:00:00', - '2011-11-01 08:00:00', - '2011-11-01 09:00:00', - '2011-11-01 10:00:00', - ) - ); - - } - - function testWeeklyByDaySpecificHour() { - - $this->parse( - 'FREQ=WEEKLY;INTERVAL=2;BYDAY=TU,WE,FR;WKST=SU', - '2011-10-07 18:00:00', - array( - '2011-10-07 18:00:00', - '2011-10-18 18:00:00', - '2011-10-19 18:00:00', - '2011-10-21 18:00:00', - '2011-11-01 18:00:00', - '2011-11-02 18:00:00', - '2011-11-04 18:00:00', - '2011-11-15 18:00:00', - '2011-11-16 18:00:00', - '2011-11-18 18:00:00', - '2011-11-29 18:00:00', - '2011-11-30 18:00:00', - ) - ); - - } - - function testMonthly() { - - $this->parse( - 'FREQ=MONTHLY;INTERVAL=3;COUNT=5', - '2011-12-05 00:00:00', - array( - '2011-12-05 00:00:00', - '2012-03-05 00:00:00', - '2012-06-05 00:00:00', - '2012-09-05 00:00:00', - '2012-12-05 00:00:00', - ) - ); - - } - - function testMonlthyEndOfMonth() { - - $this->parse( - 'FREQ=MONTHLY;INTERVAL=2;COUNT=12', - '2011-12-31 00:00:00', - array( - '2011-12-31 00:00:00', - '2012-08-31 00:00:00', - '2012-10-31 00:00:00', - '2012-12-31 00:00:00', - '2013-08-31 00:00:00', - '2013-10-31 00:00:00', - '2013-12-31 00:00:00', - '2014-08-31 00:00:00', - '2014-10-31 00:00:00', - '2014-12-31 00:00:00', - '2015-08-31 00:00:00', - '2015-10-31 00:00:00', - ) - ); - - } - - function testMonthlyByMonthDay() { - - $this->parse( - 'FREQ=MONTHLY;INTERVAL=5;COUNT=9;BYMONTHDAY=1,31,-7', - '2011-01-01 00:00:00', - array( - '2011-01-01 00:00:00', - '2011-01-25 00:00:00', - '2011-01-31 00:00:00', - '2011-06-01 00:00:00', - '2011-06-24 00:00:00', - '2011-11-01 00:00:00', - '2011-11-24 00:00:00', - '2012-04-01 00:00:00', - '2012-04-24 00:00:00', - ) - ); - - } - - function testMonthlyByDay() { - - $this->parse( - 'FREQ=MONTHLY;INTERVAL=2;COUNT=16;BYDAY=MO,-2TU,+1WE,3TH', - '2011-01-03 00:00:00', - array( - '2011-01-03 00:00:00', - '2011-01-05 00:00:00', - '2011-01-10 00:00:00', - '2011-01-17 00:00:00', - '2011-01-18 00:00:00', - '2011-01-20 00:00:00', - '2011-01-24 00:00:00', - '2011-01-31 00:00:00', - '2011-03-02 00:00:00', - '2011-03-07 00:00:00', - '2011-03-14 00:00:00', - '2011-03-17 00:00:00', - '2011-03-21 00:00:00', - '2011-03-22 00:00:00', - '2011-03-28 00:00:00', - '2011-05-02 00:00:00', - ) - ); - - } - - function testMonthlyByDayByMonthDay() { - - $this->parse( - 'FREQ=MONTHLY;COUNT=10;BYDAY=MO;BYMONTHDAY=1', - '2011-08-01 00:00:00', - array( - '2011-08-01 00:00:00', - '2012-10-01 00:00:00', - '2013-04-01 00:00:00', - '2013-07-01 00:00:00', - '2014-09-01 00:00:00', - '2014-12-01 00:00:00', - '2015-06-01 00:00:00', - '2016-02-01 00:00:00', - '2016-08-01 00:00:00', - '2017-05-01 00:00:00', - ) - ); - - } - - function testMonthlyByDayBySetPos() { - - $this->parse( - 'FREQ=MONTHLY;COUNT=10;BYDAY=MO,TU,WE,TH,FR;BYSETPOS=1,-1', - '2011-01-03 00:00:00', - array( - '2011-01-03 00:00:00', - '2011-01-31 00:00:00', - '2011-02-01 00:00:00', - '2011-02-28 00:00:00', - '2011-03-01 00:00:00', - '2011-03-31 00:00:00', - '2011-04-01 00:00:00', - '2011-04-29 00:00:00', - '2011-05-02 00:00:00', - '2011-05-31 00:00:00', - ) - ); - - } - - function testYearly() { - - $this->parse( - 'FREQ=YEARLY;COUNT=10;INTERVAL=3', - '2011-01-01 00:00:00', - array( - '2011-01-01 00:00:00', - '2014-01-01 00:00:00', - '2017-01-01 00:00:00', - '2020-01-01 00:00:00', - '2023-01-01 00:00:00', - '2026-01-01 00:00:00', - '2029-01-01 00:00:00', - '2032-01-01 00:00:00', - '2035-01-01 00:00:00', - '2038-01-01 00:00:00', - ) - ); - } - - function testYearlyLeapYear() { - - $this->parse( - 'FREQ=YEARLY;COUNT=3', - '2012-02-29 00:00:00', - array( - '2012-02-29 00:00:00', - '2016-02-29 00:00:00', - '2020-02-29 00:00:00', - ) - ); - } - - function testYearlyByMonth() { - - $this->parse( - 'FREQ=YEARLY;COUNT=8;INTERVAL=4;BYMONTH=4,10', - '2011-04-07 00:00:00', - array( - '2011-04-07 00:00:00', - '2011-10-07 00:00:00', - '2015-04-07 00:00:00', - '2015-10-07 00:00:00', - '2019-04-07 00:00:00', - '2019-10-07 00:00:00', - '2023-04-07 00:00:00', - '2023-10-07 00:00:00', - ) - ); - - } - - function testYearlyByMonthByDay() { - - $this->parse( - 'FREQ=YEARLY;COUNT=8;INTERVAL=5;BYMONTH=4,10;BYDAY=1MO,-1SU', - '2011-04-04 00:00:00', - array( - '2011-04-04 00:00:00', - '2011-04-24 00:00:00', - '2011-10-03 00:00:00', - '2011-10-30 00:00:00', - '2016-04-04 00:00:00', - '2016-04-24 00:00:00', - '2016-10-03 00:00:00', - '2016-10-30 00:00:00', - ) - ); - - } - - function testFastForward() { - - // The idea is that we're fast-forwarding too far in the future, so - // there will be no results left. - $this->parse( - 'FREQ=YEARLY;COUNT=8;INTERVAL=5;BYMONTH=4,10;BYDAY=1MO,-1SU', - '2011-04-04 00:00:00', - array(), - '2020-05-05 00:00:00' - ); - - } - - /** - * The bug that was in the - * system before would fail on the 5th tuesday of the month, if the 5th - * tuesday did not exist. - * - * A pretty slow test. Had to be marked as 'medium' for phpunit to not die - * after 1 second. Would be good to optimize later. - * - * @medium - */ - function testFifthTuesdayProblem() { - - $this->parse( - 'FREQ=MONTHLY;INTERVAL=1;UNTIL=20071030T035959Z;BYDAY=5TU', - '2007-10-04 14:46:42', - array( - "2007-10-04 14:46:42", - ) - ); - - } - - /** - * This bug came from a Fruux customer. This would result in a never-ending - * request. - */ - function testFastFowardTooFar() { - - $this->parse( - 'FREQ=WEEKLY;BYDAY=MO;UNTIL=20090704T205959Z;INTERVAL=1', - '2009-04-20 18:00:00', - array( - '2009-04-20 18:00:00', - '2009-04-27 18:00:00', - '2009-05-04 18:00:00', - '2009-05-11 18:00:00', - '2009-05-18 18:00:00', - '2009-05-25 18:00:00', - '2009-06-01 18:00:00', - '2009-06-08 18:00:00', - '2009-06-15 18:00:00', - '2009-06-22 18:00:00', - '2009-06-29 18:00:00', - ) - ); - - } - - /** - * This also at one point caused an infinite loop. We're keeping the test. - */ - function testYearlyByMonthLoop() { - - $this->parse( - 'FREQ=YEARLY;INTERVAL=1;UNTIL=20120203T225959Z;BYMONTH=2;BYSETPOS=1;BYDAY=SU,MO,TU,WE,TH,FR,SA', - '2012-01-01 15:45:00', - array( - '2012-02-01 15:45:00', - ), - '2012-01-29 23:00:00' - ); - - - } - - /** - * Something, somewhere produced an ics with an interval set to 0. Because - * this means we increase the current day (or week, month) by 0, this also - * results in an infinite loop. - * - * @expectedException InvalidArgumentException - */ - function testZeroInterval() { - - $this->parse( - 'FREQ=YEARLY;INTERVAL=0', - '2012-08-24 14:57:00', - array(), - '2013-01-01 23:00:00' - ); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testInvalidFreq() { - - $this->parse( - 'FREQ=SMONTHLY;INTERVAL=3;UNTIL=20111025T000000Z', - '2011-10-07', - array() - ); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testByDayBadOffset() { - - $this->parse( - 'FREQ=WEEKLY;INTERVAL=1;COUNT=4;BYDAY=0MO;WKST=SA', - '2014-08-01 00:00:00', - array() - ); - - } - - function testUntilBeginHAsTimezone() { - - $this->parse( - 'FREQ=WEEKLY;UNTIL=20131118T183000', - '2013-09-23 18:30:00', - array( - '2013-09-23 18:30:00', - '2013-09-30 18:30:00', - '2013-10-07 18:30:00', - '2013-10-14 18:30:00', - '2013-10-21 18:30:00', - '2013-10-28 18:30:00', - '2013-11-04 18:30:00', - '2013-11-11 18:30:00', - '2013-11-18 18:30:00', - ), - null, - 'America/New_York' - ); - - } - - function testUntilBeforeDtStart() { - - $this->parse( - 'FREQ=DAILY;UNTIL=20140101T000000Z', - '2014-08-02 00:15:00', - array( - '2014-08-02 00:15:00', - ) - ); - - } - - function testIgnoredStuff() { - - $this->parse( - 'FREQ=DAILY;BYSECOND=1;BYMINUTE=1;BYYEARDAY=1;BYWEEKNO=1;COUNT=2', - '2014-08-02 00:15:00', - array( - '2014-08-02 00:15:00', - '2014-08-03 00:15:00', - ) - ); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testUnsupportedPart() { - - $this->parse( - 'FREQ=DAILY;BYWODAN=1', - '2014-08-02 00:15:00', - array() - ); - - } - - function testIteratorFunctions() { - - $parser = new RRuleIterator('FREQ=DAILY', new DateTime('2014-08-02 00:00:13')); - $parser->next(); - $this->assertEquals( - new DateTime('2014-08-03 00:00:13'), - $parser->current() - ); - $this->assertEquals( - 1, - $parser->key() - ); - - $parser->rewind(); - - $this->assertEquals( - new DateTime('2014-08-02 00:00:13'), - $parser->current() - ); - $this->assertEquals( - 0, - $parser->key() - ); - - } - - function parse($rule, $start, $expected, $fastForward = null, $tz = 'UTC') { - - $dt = new DateTime($start, new DateTimeZone($tz)); - $parser = new RRuleIterator($rule, $dt); - - if ($fastForward) { - $parser->fastForward(new DateTime($fastForward)); - } - - $result = array(); - while($parser->valid()) { - - $item = $parser->current(); - $result[] = $item->format('Y-m-d H:i:s'); - - if ($parser->isInfinite() && count($result) >= count($expected)) { - break; - } - $parser->next(); - - } - - $this->assertEquals( - $expected, - $result - ); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/RecurrenceIterator/UntilRespectsTimezoneTest.ics Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,39 +0,0 @@ -BEGIN:VCALENDAR -VERSION:2.0 -X-WR-TIMEZONE:America/New_York -PRODID:-//www.churchcommunitybuilder.com//Church Community Builder//EN -CALSCALE:GREGORIAN -METHOD:PUBLISH -X-WR-CALNAME:Test Event -BEGIN:VTIMEZONE -TZID:America/New_York -X-LIC-LOCATION:America/New_York -BEGIN:DAYLIGHT -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -TZNAME:EDT -DTSTART:19700308T020000 -RRULE:FREQ=YEARLY;BYMONTH=3;BYDAY=2SU -END:DAYLIGHT -BEGIN:STANDARD -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -TZNAME:EST -DTSTART:19701101T020000 -RRULE:FREQ=YEARLY;BYMONTH=11;BYDAY=1SU -END:STANDARD -END:VTIMEZONE -BEGIN:VEVENT -UID:10621-1440@ccbchurch.com -DTSTART;TZID=America/New_York:20130923T183000 -DTEND;TZID=America/New_York:20130923T203000 -DTSTAMP:20131216T170211 -RRULE:FREQ=WEEKLY;UNTIL=20131118T183000 -CREATED:20130423T161111 -DESCRIPTION:Test Event ending November 11, 2013 -LAST-MODIFIED:20131126T163428 -SEQUENCE:1387231331 -SUMMARY:Test -TRANSP:OPAQUE -END:VEVENT -END:VCALENDAR
--- a/vendor/sabre/vobject/tests/VObject/SlashRTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,20 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * This issue was pointed out in Issue 55. \r should be stripped completely - * when encoding property values. - */ -class SlashRTest extends \PHPUnit_Framework_TestCase { - - function testEncode() { - - $vcal = new Component\VCalendar(); - $prop = $vcal->add('test', "abc\r\ndef"); - $this->assertEquals("TEST:abc\\ndef\r\n", $prop->serialize()); - - } - - -}
--- a/vendor/sabre/vobject/tests/VObject/Splitter/ICalendarTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,325 +0,0 @@ -<?php - -namespace Sabre\VObject\Splitter; - -use Sabre\VObject; - -class ICalendarTest extends \PHPUnit_Framework_TestCase { - - protected $version; - - function setUp() { - $this->version = VObject\Version::VERSION; - } - - function createStream($data) { - - $stream = fopen('php://memory','r+'); - fwrite($stream, $data); - rewind($stream); - return $stream; - - } - - function testICalendarImportValidEvent() { - - $data = <<<EOT -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foo -DTSTAMP:20140122T233226Z -DTSTART:20140101T070000Z -END:VEVENT -END:VCALENDAR -EOT; - $tempFile = $this->createStream($data); - - $objects = new ICalendar($tempFile); - - $return = ""; - while($object=$objects->getNext()) { - $return .= $object->serialize(); - } - $this->assertEquals(array(), VObject\Reader::read($return)->validate()); - } - - /** - * @expectedException Sabre\VObject\ParseException - */ - function testICalendarImportWrongType() { - - $data = <<<EOT -BEGIN:VCARD -UID:foo1 -END:VCARD -BEGIN:VCARD -UID:foo2 -END:VCARD -EOT; - $tempFile = $this->createStream($data); - - $objects = new ICalendar($tempFile); - - } - - function testICalendarImportEndOfData() { - $data = <<<EOT -BEGIN:VCALENDAR -BEGIN:VEVENT -UID:foo -DTSTAMP:20140122T233226Z -END:VEVENT -END:VCALENDAR -EOT; - $tempFile = $this->createStream($data); - - $objects = new ICalendar($tempFile); - - $return = ""; - while($object=$objects->getNext()) { - $return .= $object->serialize(); - } - $this->assertNull($object=$objects->getNext()); - } - - /** - * @expectedException Sabre\VObject\ParseException - */ - function testICalendarImportInvalidEvent() { - $data = <<<EOT -EOT; - $tempFile = $this->createStream($data); - $objects = new ICalendar($tempFile); - - } - - function testICalendarImportMultipleValidEvents() { - - $event[] = <<<EOT -BEGIN:VEVENT -UID:foo1 -DTSTAMP:20140122T233226Z -DTSTART:20140101T050000Z -END:VEVENT -EOT; - -$event[] = <<<EOT -BEGIN:VEVENT -UID:foo2 -DTSTAMP:20140122T233226Z -DTSTART:20140101T060000Z -END:VEVENT -EOT; - - $data = <<<EOT -BEGIN:VCALENDAR -$event[0] -$event[1] -END:VCALENDAR - -EOT; - $tempFile = $this->createStream($data); - - $objects = new ICalendar($tempFile); - - $return = ""; - $i = 0; - while($object=$objects->getNext()) { - - $expected = <<<EOT -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $this->version//EN -CALSCALE:GREGORIAN -$event[$i] -END:VCALENDAR - -EOT; - - $return .= $object->serialize(); - $expected = str_replace("\n", "\r\n", $expected); - $this->assertEquals($expected, $object->serialize()); - $i++; - } - $this->assertEquals(array(), VObject\Reader::read($return)->validate()); - } - - function testICalendarImportEventWithoutUID() { - - $data = <<<EOT -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $this->version//EN -CALSCALE:GREGORIAN -BEGIN:VEVENT -DTSTART:20140101T040000Z -DTSTAMP:20140122T233226Z -END:VEVENT -END:VCALENDAR - -EOT; - $tempFile = $this->createStream($data); - - $objects = new ICalendar($tempFile); - - $return = ""; - while($object=$objects->getNext()) { - $return .= $object->serialize(); - } - - $messages = VObject\Reader::read($return)->validate(); - - if ($messages) { - $messages = array_map( - function($item) { return $item['message']; }, - $messages - ); - $this->fail('Validation errors: ' . implode("\n", $messages)); - } else { - $this->assertEquals(array(), $messages); - } - } - - function testICalendarImportMultipleVTIMEZONESAndMultipleValidEvents() { - - $timezones = <<<EOT -BEGIN:VTIMEZONE -TZID:Europe/Berlin -BEGIN:DAYLIGHT -TZOFFSETFROM:+0100 -RRULE:FREQ=YEARLY;BYMONTH=3;BYDAY=-1SU -DTSTART:19810329T020000 -TZNAME:MESZ -TZOFFSETTO:+0200 -END:DAYLIGHT -BEGIN:STANDARD -TZOFFSETFROM:+0200 -RRULE:FREQ=YEARLY;BYMONTH=10;BYDAY=-1SU -DTSTART:19961027T030000 -TZNAME:MEZ -TZOFFSETTO:+0100 -END:STANDARD -END:VTIMEZONE -BEGIN:VTIMEZONE -TZID:Europe/London -BEGIN:DAYLIGHT -TZOFFSETFROM:+0000 -RRULE:FREQ=YEARLY;BYMONTH=3;BYDAY=-1SU -DTSTART:19810329T010000 -TZNAME:GMT+01:00 -TZOFFSETTO:+0100 -END:DAYLIGHT -BEGIN:STANDARD -TZOFFSETFROM:+0100 -RRULE:FREQ=YEARLY;BYMONTH=10;BYDAY=-1SU -DTSTART:19961027T020000 -TZNAME:GMT -TZOFFSETTO:+0000 -END:STANDARD -END:VTIMEZONE -EOT; - - $event[] = <<<EOT -BEGIN:VEVENT -UID:foo1 -DTSTAMP:20140122T232710Z -DTSTART:20140101T010000Z -END:VEVENT -EOT; - - $event[] = <<<EOT -BEGIN:VEVENT -UID:foo2 -DTSTAMP:20140122T232710Z -DTSTART:20140101T020000Z -END:VEVENT -EOT; - - $event[] = <<<EOT -BEGIN:VEVENT -UID:foo3 -DTSTAMP:20140122T232710Z -DTSTART:20140101T030000Z -END:VEVENT -EOT; - - $data = <<<EOT -BEGIN:VCALENDAR -$timezones -$event[0] -$event[1] -$event[2] -END:VCALENDAR - -EOT; - $tempFile = $this->createStream($data); - - $objects = new ICalendar($tempFile); - - $return = ""; - $i = 0; - while($object=$objects->getNext()) { - - $expected = <<<EOT -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Sabre//Sabre VObject $this->version//EN -CALSCALE:GREGORIAN -$timezones -$event[$i] -END:VCALENDAR - -EOT; - $expected = str_replace("\n", "\r\n", $expected); - - $this->assertEquals($expected, $object->serialize()); - $return .= $object->serialize(); - $i++; - - } - - $this->assertEquals(array(), VObject\Reader::read($return)->validate()); - } - - function testICalendarImportWithOutVTIMEZONES() { - - $data = <<<EOT -BEGIN:VCALENDAR -VERSION:2.0 -PRODID:-//Apple Inc.//Mac OS X 10.8//EN -CALSCALE:GREGORIAN -BEGIN:VEVENT -CREATED:20120605T072109Z -UID:D6716295-C10F-4B20-82F9-E1A3026C7DCF -DTEND;VALUE=DATE:20120717 -TRANSP:TRANSPARENT -SUMMARY:Start Vorbereitung -DTSTART;VALUE=DATE:20120716 -DTSTAMP:20120605T072115Z -SEQUENCE:2 -BEGIN:VALARM -X-WR-ALARMUID:A99EDA6A-35EB-4446-B8BC-CDA3C60C627D -UID:A99EDA6A-35EB-4446-B8BC-CDA3C60C627D -TRIGGER:-PT15H -X-APPLE-DEFAULT-ALARM:TRUE -ATTACH;VALUE=URI:Basso -ACTION:AUDIO -END:VALARM -END:VEVENT -END:VCALENDAR - -EOT; - $tempFile = $this->createStream($data); - - $objects = new ICalendar($tempFile); - - $return = ""; - while($object=$objects->getNext()) { - $return .= $object->serialize(); - } - - $messages = VObject\Reader::read($return)->validate(); - $this->assertEquals(array(), $messages); - } - -}
--- a/vendor/sabre/vobject/tests/VObject/Splitter/VCardTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,195 +0,0 @@ -<?php - -namespace Sabre\VObject\Splitter; - -use Sabre\VObject; - -class VCardTest extends \PHPUnit_Framework_TestCase { - - function createStream($data) { - - $stream = fopen('php://memory','r+'); - fwrite($stream, $data); - rewind($stream); - return $stream; - - } - - function testVCardImportValidVCard() { - $data = <<<EOT -BEGIN:VCARD -UID:foo -END:VCARD -EOT; - $tempFile = $this->createStream($data); - - $objects = new VCard($tempFile); - - $count = 0; - while($objects->getNext()) { - $count++; - } - $this->assertEquals(1, $count); - - } - - /** - * @expectedException Sabre\VObject\ParseException - */ - function testVCardImportWrongType() { - $event[] = <<<EOT -BEGIN:VEVENT -UID:foo1 -DTSTAMP:20140122T233226Z -DTSTART:20140101T050000Z -END:VEVENT -EOT; - -$event[] = <<<EOT -BEGIN:VEVENT -UID:foo2 -DTSTAMP:20140122T233226Z -DTSTART:20140101T060000Z -END:VEVENT -EOT; - - $data = <<<EOT -BEGIN:VCALENDAR -$event[0] -$event[1] -END:VCALENDAR - -EOT; - $tempFile = $this->createStream($data); - - $splitter = new VCard($tempFile); - - while($object=$splitter->getNext()) { - } - - } - - function testVCardImportValidVCardsWithCategories() { - $data = <<<EOT -BEGIN:VCARD -UID:card-in-foo1-and-foo2 -CATEGORIES:foo1,foo2 -END:VCARD -BEGIN:VCARD -UID:card-in-foo1 -CATEGORIES:foo1 -END:VCARD -BEGIN:VCARD -UID:card-in-foo3 -CATEGORIES:foo3 -END:VCARD -BEGIN:VCARD -UID:card-in-foo1-and-foo3 -CATEGORIES:foo1\,foo3 -END:VCARD -EOT; - $tempFile = $this->createStream($data); - - $splitter = new VCard($tempFile); - - $count = 0; - while($object=$splitter->getNext()) { - $count++; - } - $this->assertEquals(4, $count); - - } - - function testVCardImportEndOfData() { - $data = <<<EOT -BEGIN:VCARD -UID:foo -END:VCARD -EOT; - $tempFile = $this->createStream($data); - - $objects = new VCard($tempFile); - $object=$objects->getNext(); - - $this->assertNull($objects->getNext()); - - - } - - /** - * @expectedException \Sabre\VObject\ParseException - */ - function testVCardImportCheckInvalidArgumentException() { - $data = <<<EOT -BEGIN:FOO -END:FOO -EOT; - $tempFile = $this->createStream($data); - - $objects = new VCard($tempFile); - while($objects->getNext()) { } - - } - - function testVCardImportMultipleValidVCards() { - $data = <<<EOT -BEGIN:VCARD -UID:foo -END:VCARD -BEGIN:VCARD -UID:foo -END:VCARD -EOT; - $tempFile = $this->createStream($data); - - $objects = new VCard($tempFile); - - $count = 0; - while($objects->getNext()) { - $count++; - } - $this->assertEquals(2, $count); - - } - - function testImportMultipleSeparatedWithNewLines() { - $data = <<<EOT -BEGIN:VCARD -UID:foo -END:VCARD - - -BEGIN:VCARD -UID:foo -END:VCARD - - -EOT; - $tempFile = $this->createStream($data); - $objects = new VCard($tempFile); - - $count = 0; - while ($objects->getNext()) { - $count++; - } - $this->assertEquals(2, $count); - } - - function testVCardImportVCardWithoutUID() { - $data = <<<EOT -BEGIN:VCARD -END:VCARD -EOT; - $tempFile = $this->createStream($data); - - $objects = new VCard($tempFile); - - $count = 0; - while($objects->getNext()) { - $count++; - } - - $this->assertEquals(1, $count); - } - -}
--- a/vendor/sabre/vobject/tests/VObject/StringUtilTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,55 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class StringUtilTest extends \PHPUnit_Framework_TestCase { - - function testNonUTF8() { - - $string = StringUtil::isUTF8(chr(0xbf)); - - $this->assertEquals(false, $string); - - } - - function testIsUTF8() { - - $string = StringUtil::isUTF8('I 💚 SabreDAV'); - - $this->assertEquals(true, $string); - - } - - function testUTF8ControlChar() { - - $string = StringUtil::isUTF8(chr(0x00)); - - $this->assertEquals(false, $string); - - } - - function testConvertToUTF8nonUTF8() { - - $string = StringUtil::convertToUTF8(chr(0xbf)); - - $this->assertEquals(utf8_encode(chr(0xbf)), $string); - - } - - function testConvertToUTF8IsUTF8() { - - $string = StringUtil::convertToUTF8('I 💚 SabreDAV'); - - $this->assertEquals('I 💚 SabreDAV', $string); - - } - - function testConvertToUTF8ControlChar() { - - $string = StringUtil::convertToUTF8(chr(0x00)); - - $this->assertEquals('', $string); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/TestCase.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,50 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class TestCase extends \PHPUnit_Framework_TestCase { - - /** - * This method tests wether two vcards or icalendar objects are - * semantically identical. - * - * It supports objects being supplied as strings, streams or - * Sabre\VObject\Component instances. - * - * PRODID is removed from both objects as this is often variable. - * - * @param resource|string|Component $expected - * @param resource|string|Component $actual - * @param string $message - */ - function assertVObjEquals($expected, $actual, $message = '') { - - $self = $this; - $getObj = function($input) use ($self) { - - if (is_resource($input)) { - $input = stream_get_contents($input); - } - if (is_string($input)) { - $input = Reader::read($input); - } - if (!$input instanceof Component) { - $this->fail('Input must be a string, stream or VObject component'); - } - unset($input->PRODID); - return $input; - - }; - - $expected = $getObj($expected); - $actual = $getObj($actual); - - $this->assertEquals( - $expected->serialize(), - $actual->serialize(), - $message - ); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/TimeZoneUtilTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,360 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class TimezoneUtilTest extends \PHPUnit_Framework_TestCase { - - function setUp() { - - // clearning the tz cache - TimezoneUtil::$map = null; - - } - - /** - * @dataProvider getMapping - */ - function testCorrectTZ($timezoneName) { - - $tz = new \DateTimeZone($timezoneName); - $this->assertInstanceOf('DateTimeZone', $tz); - - } - - function getMapping() { - - TimeZoneUtil::loadTzMaps(); - - // PHPUNit requires an array of arrays - return array_map( - function($value) { - return array($value); - }, - TimeZoneUtil::$map - ); - - } - - function testExchangeMap() { - - $vobj = <<<HI -BEGIN:VCALENDAR -METHOD:REQUEST -VERSION:2.0 -BEGIN:VTIMEZONE -TZID:foo -X-MICROSOFT-CDO-TZID:2 -BEGIN:STANDARD -DTSTART:16010101T030000 -TZOFFSETFROM:+0200 -TZOFFSETTO:+0100 -RRULE:FREQ=YEARLY;WKST=MO;INTERVAL=1;BYMONTH=10;BYDAY=-1SU -END:STANDARD -BEGIN:DAYLIGHT -DTSTART:16010101T020000 -TZOFFSETFROM:+0100 -TZOFFSETTO:+0200 -RRULE:FREQ=YEARLY;WKST=MO;INTERVAL=1;BYMONTH=3;BYDAY=-1SU -END:DAYLIGHT -END:VTIMEZONE -BEGIN:VEVENT -DTSTAMP:20120416T092149Z -DTSTART;TZID="foo":20120418T1 - 00000 -SUMMARY:Begin Unterhaltsreinigung -UID:040000008200E00074C5B7101A82E0080000000010DA091DC31BCD01000000000000000 - 0100000008FECD2E607780649BE5A4C9EE6418CBC - 000 -END:VEVENT -END:VCALENDAR -HI; - - $tz = TimeZoneUtil::getTimeZone('foo', Reader::read($vobj)); - $ex = new \DateTimeZone('Europe/Lisbon'); - - $this->assertEquals($ex->getName(), $tz->getName()); - - } - - function testWetherMicrosoftIsStillInsane() { - - $vobj = <<<HI -BEGIN:VCALENDAR -METHOD:REQUEST -VERSION:2.0 -BEGIN:VTIMEZONE -TZID:(GMT+01.00) Sarajevo/Warsaw/Zagreb -X-MICROSOFT-CDO-TZID:2 -BEGIN:STANDARD -DTSTART:16010101T030000 -TZOFFSETFROM:+0200 -TZOFFSETTO:+0100 -RRULE:FREQ=YEARLY;WKST=MO;INTERVAL=1;BYMONTH=10;BYDAY=-1SU -END:STANDARD -END:VTIMEZONE -END:VCALENDAR -HI; - - $tz = TimeZoneUtil::getTimeZone('(GMT+01.00) Sarajevo/Warsaw/Zagreb', Reader::read($vobj)); - $ex = new \DateTimeZone('Europe/Sarajevo'); - - $this->assertEquals($ex->getName(), $tz->getName()); - - } - - function testUnknownExchangeId() { - - $vobj = <<<HI -BEGIN:VCALENDAR -METHOD:REQUEST -VERSION:2.0 -BEGIN:VTIMEZONE -TZID:foo -X-MICROSOFT-CDO-TZID:2000 -BEGIN:STANDARD -DTSTART:16010101T030000 -TZOFFSETFROM:+0200 -TZOFFSETTO:+0100 -RRULE:FREQ=YEARLY;WKST=MO;INTERVAL=1;BYMONTH=10;BYDAY=-1SU -END:STANDARD -BEGIN:DAYLIGHT -DTSTART:16010101T020000 -TZOFFSETFROM:+0100 -TZOFFSETTO:+0200 -RRULE:FREQ=YEARLY;WKST=MO;INTERVAL=1;BYMONTH=3;BYDAY=-1SU -END:DAYLIGHT -END:VTIMEZONE -BEGIN:VEVENT -DTSTAMP:20120416T092149Z -DTSTART;TZID="foo":20120418T1 - 00000 -SUMMARY:Begin Unterhaltsreinigung -UID:040000008200E00074C5B7101A82E0080000000010DA091DC31BCD01000000000000000 - 0100000008FECD2E607780649BE5A4C9EE6418CBC -DTEND;TZID="Sarajevo, Skopje, Sofija, Vilnius, Warsaw, Zagreb":20120418T103 - 000 -END:VEVENT -END:VCALENDAR -HI; - - $tz = TimeZoneUtil::getTimeZone('foo', Reader::read($vobj)); - $ex = new \DateTimeZone(date_default_timezone_get()); - $this->assertEquals($ex->getName(), $tz->getName()); - - } - - function testWindowsTimeZone() { - - $tz = TimeZoneUtil::getTimeZone('Eastern Standard Time'); - $ex = new \DateTimeZone('America/New_York'); - $this->assertEquals($ex->getName(), $tz->getName()); - - } - - /** - * @dataProvider getPHPTimeZoneIdentifiers - */ - function testTimeZoneIdentifiers($tzid) { - - $tz = TimeZoneUtil::getTimeZone($tzid); - $ex = new \DateTimeZone($tzid); - - $this->assertEquals($ex->getName(), $tz->getName()); - - } - - /** - * @dataProvider getPHPTimeZoneBCIdentifiers - */ - function testTimeZoneBCIdentifiers($tzid) { - - $tz = TimeZoneUtil::getTimeZone($tzid); - $ex = new \DateTimeZone($tzid); - - $this->assertEquals($ex->getName(), $tz->getName()); - - } - - function getPHPTimeZoneIdentifiers() { - - // PHPUNit requires an array of arrays - return array_map( - function($value) { - return array($value); - }, - \DateTimeZone::listIdentifiers() - ); - - } - - function getPHPTimeZoneBCIdentifiers() { - - // PHPUNit requires an array of arrays - return array_map( - function($value) { - return array($value); - }, - TimeZoneUtil::getIdentifiersBC() - ); - - } - - function testTimezoneOffset() { - - $tz = TimeZoneUtil::getTimeZone('GMT-0400', null, true); - - if (version_compare(PHP_VERSION, '5.5.10', '>=') && !defined('HHVM_VERSION')) { - $ex = new \DateTimeZone('-04:00'); - } else { - $ex = new \DateTimeZone('Etc/GMT-4'); - } - $this->assertEquals($ex->getName(), $tz->getName()); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testTimezoneFail() { - - $tz = TimeZoneUtil::getTimeZone('FooBar', null, true); - - } - - function testFallBack() { - - $vobj = <<<HI -BEGIN:VCALENDAR -METHOD:REQUEST -VERSION:2.0 -BEGIN:VTIMEZONE -TZID:foo -BEGIN:STANDARD -DTSTART:16010101T030000 -TZOFFSETFROM:+0200 -TZOFFSETTO:+0100 -RRULE:FREQ=YEARLY;WKST=MO;INTERVAL=1;BYMONTH=10;BYDAY=-1SU -END:STANDARD -BEGIN:DAYLIGHT -DTSTART:16010101T020000 -TZOFFSETFROM:+0100 -TZOFFSETTO:+0200 -RRULE:FREQ=YEARLY;WKST=MO;INTERVAL=1;BYMONTH=3;BYDAY=-1SU -END:DAYLIGHT -END:VTIMEZONE -BEGIN:VEVENT -DTSTAMP:20120416T092149Z -DTSTART;TZID="foo":20120418T1 - 00000 -SUMMARY:Begin Unterhaltsreinigung -UID:040000008200E00074C5B7101A82E0080000000010DA091DC31BCD01000000000000000 - 0100000008FECD2E607780649BE5A4C9EE6418CBC - 000 -END:VEVENT -END:VCALENDAR -HI; - - $tz = TimeZoneUtil::getTimeZone('foo', Reader::read($vobj)); - $ex = new \DateTimeZone(date_default_timezone_get()); - $this->assertEquals($ex->getName(), $tz->getName()); - - } - - function testLjubljanaBug() { - - $vobj = <<<HI -BEGIN:VCALENDAR -CALSCALE:GREGORIAN -PRODID:-//Ximian//NONSGML Evolution Calendar//EN -VERSION:2.0 -BEGIN:VTIMEZONE -TZID:/freeassociation.sourceforge.net/Tzfile/Europe/Ljubljana -X-LIC-LOCATION:Europe/Ljubljana -BEGIN:STANDARD -TZNAME:CET -DTSTART:19701028T030000 -RRULE:FREQ=YEARLY;BYDAY=-1SU;BYMONTH=10 -TZOFFSETFROM:+0200 -TZOFFSETTO:+0100 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:CEST -DTSTART:19700325T020000 -RRULE:FREQ=YEARLY;BYDAY=-1SU;BYMONTH=3 -TZOFFSETFROM:+0100 -TZOFFSETTO:+0200 -END:DAYLIGHT -END:VTIMEZONE -BEGIN:VEVENT -UID:foo -DTSTART;TZID=/freeassociation.sourceforge.net/Tzfile/Europe/Ljubljana: - 20121003T080000 -DTEND;TZID=/freeassociation.sourceforge.net/Tzfile/Europe/Ljubljana: - 20121003T083000 -TRANSP:OPAQUE -SEQUENCE:2 -SUMMARY:testing -CREATED:20121002T172613Z -LAST-MODIFIED:20121002T172613Z -END:VEVENT -END:VCALENDAR - -HI; - - - $tz = TimeZoneUtil::getTimeZone('/freeassociation.sourceforge.net/Tzfile/Europe/Ljubljana', Reader::read($vobj)); - $ex = new \DateTimeZone('Europe/Ljubljana'); - $this->assertEquals($ex->getName(), $tz->getName()); - - } - - function testWeirdSystemVLICs() { - -$vobj = <<<HI -BEGIN:VCALENDAR -CALSCALE:GREGORIAN -PRODID:-//Ximian//NONSGML Evolution Calendar//EN -VERSION:2.0 -BEGIN:VTIMEZONE -TZID:/freeassociation.sourceforge.net/Tzfile/SystemV/EST5EDT -X-LIC-LOCATION:SystemV/EST5EDT -BEGIN:STANDARD -TZNAME:EST -DTSTART:19701104T020000 -RRULE:FREQ=YEARLY;BYDAY=1SU;BYMONTH=11 -TZOFFSETFROM:-0400 -TZOFFSETTO:-0500 -END:STANDARD -BEGIN:DAYLIGHT -TZNAME:EDT -DTSTART:19700311T020000 -RRULE:FREQ=YEARLY;BYDAY=2SU;BYMONTH=3 -TZOFFSETFROM:-0500 -TZOFFSETTO:-0400 -END:DAYLIGHT -END:VTIMEZONE -BEGIN:VEVENT -UID:20121026T021107Z-6301-1000-1-0@chAir -DTSTAMP:20120905T172126Z -DTSTART;TZID=/freeassociation.sourceforge.net/Tzfile/SystemV/EST5EDT: - 20121026T153000 -DTEND;TZID=/freeassociation.sourceforge.net/Tzfile/SystemV/EST5EDT: - 20121026T160000 -TRANSP:OPAQUE -SEQUENCE:5 -SUMMARY:pick up Ibby -CLASS:PUBLIC -CREATED:20121026T021108Z -LAST-MODIFIED:20121026T021118Z -X-EVOLUTION-MOVE-CALENDAR:1 -END:VEVENT -END:VCALENDAR -HI; - - $tz = TimeZoneUtil::getTimeZone('/freeassociation.sourceforge.net/Tzfile/SystemV/EST5EDT', Reader::read($vobj), true); - $ex = new \DateTimeZone('America/New_York'); - $this->assertEquals($ex->getName(), $tz->getName()); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/UUIDUtilTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,37 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class UUIDUtilTest extends \PHPUnit_Framework_TestCase { - - function testValidateUUID() { - - $this->assertTrue( - UUIDUtil::validateUUID('11111111-2222-3333-4444-555555555555') - ); - $this->assertFalse( - UUIDUtil::validateUUID(' 11111111-2222-3333-4444-555555555555') - ); - $this->assertTrue( - UUIDUtil::validateUUID('ffffffff-2222-3333-4444-555555555555') - ); - $this->assertFalse( - UUIDUtil::validateUUID('fffffffg-2222-3333-4444-555555555555') - ); - - } - - /** - * @depends testValidateUUID - */ - function testGetUUID() { - - $this->assertTrue( - UUIDUtil::validateUUID( - UUIDUtil::getUUID() - ) - ); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/VCard21Test.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,52 +0,0 @@ -<?php - -namespace Sabre\VObject; - -/** - * Assorted vcard 2.1 tests. - */ -class VCard21Test extends \PHPUnit_Framework_TestCase { - - function testPropertyWithNoName() { - - $input = <<<VCF -BEGIN:VCARD\r -VERSION:2.1\r -EMAIL;HOME;WORK:evert@fruux.com\r -END:VCARD\r - -VCF; - - $vobj = Reader::read($input); - $output = $vobj->serialize($input); - - $this->assertEquals($input, $output); - - } - - function testPropertyPadValueCount() { - - $input = <<<VCF -BEGIN:VCARD -VERSION:2.1 -N:Foo -END:VCARD - -VCF; - - $vobj = Reader::read($input); - $output = $vobj->serialize($input); - - $expected = <<<VCF -BEGIN:VCARD\r -VERSION:2.1\r -N:Foo;;;;\r -END:VCARD\r - -VCF; - - - $this->assertEquals($expected, $output); - - } -}
--- a/vendor/sabre/vobject/tests/VObject/VCardConverterTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,531 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class VCardConverterTest extends TestCase { - - function testConvert30to40() { - - $input = <<<IN -BEGIN:VCARD -VERSION:3.0 -PRODID:foo -FN;CHARSET=UTF-8:Steve -TEL;TYPE=PREF,HOME:+1 555 666 777 -ITEM1.TEL:+1 444 555 666 -ITEM1.X-ABLABEL:CustomLabel -PHOTO;ENCODING=b;TYPE=JPEG,HOME:Zm9v -PHOTO;ENCODING=b;TYPE=GIF:Zm9v -PHOTO;X-PARAM=FOO;ENCODING=b;TYPE=PNG:Zm9v -PHOTO;VALUE=URI:http://example.org/foo.png -X-ABShowAs:COMPANY -END:VCARD -IN; - - $output = <<<OUT -BEGIN:VCARD -VERSION:4.0 -FN:Steve -TEL;PREF=1;TYPE=HOME:+1 555 666 777 -ITEM1.TEL:+1 444 555 666 -ITEM1.X-ABLABEL:CustomLabel -PHOTO;TYPE=HOME:data:image/jpeg;base64,Zm9v -PHOTO:data:image/gif;base64,Zm9v -PHOTO;X-PARAM=FOO:data:image/png;base64,Zm9v -PHOTO:http://example.org/foo.png -KIND:ORG -END:VCARD -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD40); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - function testConvert40to40() { - - $input = <<<IN -BEGIN:VCARD -VERSION:4.0 -FN:Steve -TEL;PREF=1;TYPE=HOME:+1 555 666 777 -PHOTO:data:image/jpeg;base64,Zm9v -PHOTO:data:image/gif;base64,Zm9v -PHOTO;X-PARAM=FOO:data:image/png;base64,Zm9v -PHOTO:http://example.org/foo.png -END:VCARD - -IN; - - $output = <<<OUT -BEGIN:VCARD -VERSION:4.0 -FN:Steve -TEL;PREF=1;TYPE=HOME:+1 555 666 777 -PHOTO:data:image/jpeg;base64,Zm9v -PHOTO:data:image/gif;base64,Zm9v -PHOTO;X-PARAM=FOO:data:image/png;base64,Zm9v -PHOTO:http://example.org/foo.png -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD40); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - function testConvert21to40() { - - $input = <<<IN -BEGIN:VCARD -VERSION:2.1 -N:Family;Johnson -FN:Johnson Family -TEL;HOME;VOICE:555-12345-345 -ADR;HOME:;;100 Street Lane;Saubel Beach;ON;H0H0H0 -LABEL;HOME;ENCODING=QUOTED-PRINTABLE:100 Street Lane=0D=0ASaubel Beach, - ON H0H0H0 -REV:20110731T040251Z -UID:12345678 -END:VCARD -IN; - - $output = <<<OUT -BEGIN:VCARD -VERSION:4.0 -N:Family;Johnson;;; -FN:Johnson Family -TEL;TYPE=HOME,VOICE:555-12345-345 -ADR;TYPE=HOME:;;100 Street Lane;Saubel Beach;ON;H0H0H0; -REV:20110731T040251Z -UID:12345678 -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD40); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - function testConvert30to30() { - - $input = <<<IN -BEGIN:VCARD -VERSION:3.0 -PRODID:foo -FN;CHARSET=UTF-8:Steve -TEL;TYPE=PREF,HOME:+1 555 666 777 -PHOTO;ENCODING=b;TYPE=JPEG:Zm9v -PHOTO;ENCODING=b;TYPE=GIF:Zm9v -PHOTO;X-PARAM=FOO;ENCODING=b;TYPE=PNG:Zm9v -PHOTO;VALUE=URI:http://example.org/foo.png -END:VCARD - -IN; - - $output = <<<OUT -BEGIN:VCARD -VERSION:3.0 -PRODID:foo -FN;CHARSET=UTF-8:Steve -TEL;TYPE=PREF,HOME:+1 555 666 777 -PHOTO;ENCODING=b;TYPE=JPEG:Zm9v -PHOTO;ENCODING=b;TYPE=GIF:Zm9v -PHOTO;X-PARAM=FOO;ENCODING=b;TYPE=PNG:Zm9v -PHOTO;VALUE=URI:http://example.org/foo.png -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD30); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - function testConvert40to30() { - - $input = <<<IN -BEGIN:VCARD -VERSION:4.0 -PRODID:foo -FN:Steve -TEL;PREF=1;TYPE=HOME:+1 555 666 777 -PHOTO:data:image/jpeg;base64,Zm9v -PHOTO:data:image/gif,foo -PHOTO;X-PARAM=FOO:data:image/png;base64,Zm9v -PHOTO:http://example.org/foo.png -KIND:ORG -END:VCARD - -IN; - - $output = <<<OUT -BEGIN:VCARD -VERSION:3.0 -FN:Steve -TEL;TYPE=PREF,HOME:+1 555 666 777 -PHOTO;ENCODING=b;TYPE=JPEG:Zm9v -PHOTO;ENCODING=b;TYPE=GIF:Zm9v -PHOTO;ENCODING=b;TYPE=PNG;X-PARAM=FOO:Zm9v -PHOTO;VALUE=URI:http://example.org/foo.png -X-ABSHOWAS:COMPANY -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD30); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - function testConvertGroupCard() { - - $input = <<<IN -BEGIN:VCARD -VERSION:3.0 -PRODID:foo -X-ADDRESSBOOKSERVER-KIND:GROUP -END:VCARD - -IN; - - $output = <<<OUT -BEGIN:VCARD -VERSION:4.0 -KIND:GROUP -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD40); - - $this->assertVObjEquals( - $output, - $vcard - ); - - $input = $output; - $output = <<<OUT -BEGIN:VCARD -VERSION:3.0 -X-ADDRESSBOOKSERVER-KIND:GROUP -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD30); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - function testBDAYConversion() { - - $input = <<<IN -BEGIN:VCARD -VERSION:3.0 -PRODID:foo -BDAY;X-APPLE-OMIT-YEAR=1604:1604-04-16 -END:VCARD - -IN; - - $output = <<<OUT -BEGIN:VCARD -VERSION:4.0 -BDAY:--04-16 -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD40); - - $this->assertVObjEquals( - $output, - $vcard - ); - - $input = $output; - $output = <<<OUT -BEGIN:VCARD -VERSION:3.0 -BDAY;X-APPLE-OMIT-YEAR=1604:1604-04-16 -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD30); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testUnknownSourceVCardVersion() { - - $input = <<<IN -BEGIN:VCARD -VERSION:4.2 -PRODID:foo -FN;CHARSET=UTF-8:Steve -TEL;TYPE=PREF,HOME:+1 555 666 777 -ITEM1.TEL:+1 444 555 666 -ITEM1.X-ABLABEL:CustomLabel -PHOTO;ENCODING=b;TYPE=JPEG,HOME:Zm9v -PHOTO;ENCODING=b;TYPE=GIF:Zm9v -PHOTO;X-PARAM=FOO;ENCODING=b;TYPE=PNG:Zm9v -PHOTO;VALUE=URI:http://example.org/foo.png -X-ABShowAs:COMPANY -END:VCARD - -IN; - - $vcard = Reader::read($input); - $vcard->convert(Document::VCARD40); - - } - - /** - * @expectedException InvalidArgumentException - */ - function testUnknownTargetVCardVersion() { - - $input = <<<IN -BEGIN:VCARD -VERSION:3.0 -PRODID:foo -END:VCARD - -IN; - - $vcard = Reader::read($input); - $vcard->convert(Document::VCARD21); - - } - - function testConvertIndividualCard() { - - $input = <<<IN -BEGIN:VCARD -VERSION:4.0 -PRODID:foo -KIND:INDIVIDUAL -END:VCARD - -IN; - - $output = <<<OUT -BEGIN:VCARD -VERSION:3.0 -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD30); - - $this->assertVObjEquals( - $output, - $vcard - ); - - $input = $output; - $output = <<<OUT -BEGIN:VCARD -VERSION:4.0 -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD40); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - function testAnniversary() { - - $input = <<<IN -BEGIN:VCARD -VERSION:4.0 -ITEM1.ANNIVERSARY:20081210 -END:VCARD - -IN; - - $output = <<<'OUT' -BEGIN:VCARD -VERSION:3.0 -ITEM1.X-ABDATE;VALUE=DATE-AND-OR-TIME:20081210 -ITEM1.X-ABLABEL:_$!<Anniversary>!$_ -ITEM1.X-ANNIVERSARY;VALUE=DATE-AND-OR-TIME:20081210 -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD30); - - $this->assertVObjEquals( - $output, - $vcard - ); - - // Swapping input and output - list( - $input, - $output - ) = array( - $output, - $input - ); - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD40); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - function testMultipleAnniversaries() { - - $input = <<<IN -BEGIN:VCARD -VERSION:4.0 -ITEM1.ANNIVERSARY:20081210 -ITEM2.ANNIVERSARY:20091210 -ITEM3.ANNIVERSARY:20101210 -END:VCARD - -IN; - - $output = <<<'OUT' -BEGIN:VCARD -VERSION:3.0 -ITEM1.X-ABDATE;VALUE=DATE-AND-OR-TIME:20081210 -ITEM1.X-ABLABEL:_$!<Anniversary>!$_ -ITEM1.X-ANNIVERSARY;VALUE=DATE-AND-OR-TIME:20081210 -ITEM2.X-ABDATE;VALUE=DATE-AND-OR-TIME:20091210 -ITEM2.X-ABLABEL:_$!<Anniversary>!$_ -ITEM2.X-ANNIVERSARY;VALUE=DATE-AND-OR-TIME:20091210 -ITEM3.X-ABDATE;VALUE=DATE-AND-OR-TIME:20101210 -ITEM3.X-ABLABEL:_$!<Anniversary>!$_ -ITEM3.X-ANNIVERSARY;VALUE=DATE-AND-OR-TIME:20101210 -END:VCARD - -OUT; - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD30); - - $this->assertVObjEquals( - $output, - $vcard - ); - - // Swapping input and output - list( - $input, - $output - ) = array( - $output, - $input - ); - - $vcard = Reader::read($input); - $vcard = $vcard->convert(Document::VCARD40); - - $this->assertVObjEquals( - $output, - $vcard - ); - - } - - function testNoLabel() { - - $input = <<<VCF -BEGIN:VCARD -VERSION:3.0 -UID:foo -N:Doe;John;;; -FN:John Doe -item1.X-ABDATE;type=pref:2008-12-11 -END:VCARD - -VCF; - - $vcard = Reader::read($input); - - $this->assertInstanceOf('Sabre\\VObject\\Component\\VCard', $vcard); - $vcard = $vcard->convert(Document::VCARD40); - $vcard = $vcard->serialize(); - - $converted = Reader::read($vcard); - $converted->validate(); - - $version = Version::VERSION; - - $expected = <<<VCF -BEGIN:VCARD -VERSION:4.0 -PRODID:-//Sabre//Sabre VObject $version//EN -UID:foo -N:Doe;John;;; -FN:John Doe -ITEM1.X-ABDATE;PREF=1:2008-12-11 -END:VCARD - -VCF; - - $this->assertEquals($expected, str_replace("\r","", $vcard)); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/VersionTest.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,14 +0,0 @@ -<?php - -namespace Sabre\VObject; - -class VersionTest extends \PHPUnit_Framework_TestCase { - - function testString() { - - $v = Version::VERSION; - $this->assertEquals(-1, version_compare('2.0.0',$v)); - - } - -}
--- a/vendor/sabre/vobject/tests/VObject/issue153.vcf Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,352 +0,0 @@ -BEGIN:VCARD -VERSION:3.0 -N:Benutzer;Test;;; -FN:Test Benutzer -PHOTO;BASE64: - /9j/4AAQSkZJRgABAQAAAQABAAD/4QBYRXhpZgAATU0AKgAAAAgAAgESAAMAAAABAAEAAIdpAAQA - AAABAAAAJgAAAAAAA6ABAAMAAAABAAEAAKACAAQAAAABAAABQKADAAQAAAABAAABQAAAAAD/2wBD - AAIBAQIBAQICAQICAgICAwUDAwMDAwYEBAMFBwYHBwcGBgYHCAsJBwgKCAYGCQ0JCgsLDAwMBwkN - Dg0MDgsMDAv/2wBDAQICAgMCAwUDAwULCAYICwsLCwsLCwsLCwsLCwsLCwsLCwsLCwsLCwsLCwsL - CwsLCwsLCwsLCwsLCwsLCwsLCwv/wAARCAFAAUADASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAA - AAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIhMUEGE1FhByJxFDKB - kaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZn - aGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT - 1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEAAwEBAQEBAQEBAQAAAAAAAAECAwQFBgcI - CQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAV - YnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6 - goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk - 5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD8J7JbO8tYo1tIFCDLOVG5qfdaVZRwmSOFWzyA - F4H1rLt5WViMhdp6HgmtKK8O3B+4Rhx6fSgBI9FtjaNN5aErwRjilSys7lFAt41xyTtqc2yJCVlY - 7eqgGqv2jyLcebjZnGPWncdzT0+w0u5eQXtrGiBcIyoPmNMXwpb/AGMTSRRbH6YAyPwqK21GKdfL - BAVfu+1SQX4jnjKFsp03dPypCKN9oEaKSkC7R0bGKpnSlSPdHErZOORXV3Ouy337sCLB6kpx+FY0 - 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 - zbVbk4/OrNpefLsnyyg5UUAf/9k= -END:VCARD
--- a/vendor/sabre/vobject/tests/VObject/issue64.vcf Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,351 +0,0 @@ -BEGIN:VCARD -VERSION:2.1 -PHOTO;ENCODING=BASE64;JPEG: - /9j/4AAQSkZJRgABAQAAAQABAAD/4QBYRXhpZgAATU0AKgAAAAgAAgESAAMAAAABAAEAAIdpAAQA - AAABAAAAJgAAAAAAA6ABAAMAAAABAAEAAKACAAQAAAABAAABQKADAAQAAAABAAABQAAAAAD/2wBD - AAIBAQIBAQICAQICAgICAwUDAwMDAwYEBAMFBwYHBwcGBgYHCAsJBwgKCAYGCQ0JCgsLDAwMBwkN - Dg0MDgsMDAv/2wBDAQICAgMCAwUDAwULCAYICwsLCwsLCwsLCwsLCwsLCwsLCwsLCwsLCwsLCwsL - CwsLCwsLCwsLCwsLCwsLCwsLCwv/wAARCAFAAUADASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAA - AAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIhMUEGE1FhByJxFDKB - kaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZn - aGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT - 1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEAAwEBAQEBAQEBAQAAAAAAAAECAwQFBgcI - CQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAV - YnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6 - goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk - 5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD8J7JbO8tYo1tIFCDLOVG5qfdaVZRwmSOFWzyA - F4H1rLt5WViMhdp6HgmtKK8O3B+4Rhx6fSgBI9FtjaNN5aErwRjilSys7lFAt41xyTtqc2yJCVlY - 7eqgGqv2jyLcebjZnGPWncdzT0+w0u5eQXtrGiBcIyoPmNMXwpb/AGMTSRRbH6YAyPwqK21GKdfL - BAVfu+1SQX4jnjKFsp03dPypCKN9oEaKSkC7R0bGKpnSlSPdHErZOORXV3Ouy337sCLB6kpx+FY0 - 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 - zbVbk4/OrNpefLsnyyg5UUAf/9k= - -END:VCARD
--- a/vendor/sabre/vobject/tests/bootstrap.php Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,25 +0,0 @@ -<?php - -date_default_timezone_set('UTC'); - -$try = array( - __DIR__ . '/../vendor/autoload.php', - __DIR__ . '/../../../autoload.php', -); - -foreach($try as $path) { - if (file_exists($path)) { - $autoLoader = include $path; - break; - } -} - -$autoLoader->addPsr4('Sabre\\VObject\\',__DIR__ . '/VObject'); - -if (!defined('SABRE_TEMPDIR')) { - define('SABRE_TEMPDIR', __DIR__ . '/temp/'); -} - -if (!file_exists(SABRE_TEMPDIR)) { - mkdir(SABRE_TEMPDIR); -}
--- a/vendor/sabre/vobject/tests/phpcs/ruleset.xml Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,57 +0,0 @@ -<?xml version="1.0"?> -<ruleset name="sabre.php"> - <description>sabre.io codesniffer ruleset</description> - - <!-- Include the whole PSR-1 standard --> - <rule ref="PSR1" /> - - <!-- All PHP files MUST use the Unix LF (linefeed) line ending. --> - <rule ref="Generic.Files.LineEndings"> - <properties> - <property name="eolChar" value="\n"/> - </properties> - </rule> - - <!-- The closing ?> tag MUST be omitted from files containing only PHP. --> - <rule ref="Zend.Files.ClosingTag"/> - - <!-- There MUST NOT be trailing whitespace at the end of non-blank lines. --> - <rule ref="Squiz.WhiteSpace.SuperfluousWhitespace"> - <properties> - <property name="ignoreBlankLines" value="true"/> - </properties> - </rule> - - <!-- There MUST NOT be more than one statement per line. --> - <rule ref="Generic.Formatting.DisallowMultipleStatements"/> - - <rule ref="Generic.WhiteSpace.ScopeIndent"> - <properties> - <property name="ignoreIndentationTokens" type="array" value="T_COMMENT,T_DOC_COMMENT"/> - </properties> - </rule> - <rule ref="Generic.WhiteSpace.DisallowTabIndent"/> - - <!-- PHP keywords MUST be in lower case. --> - <rule ref="Generic.PHP.LowerCaseKeyword"/> - - <!-- The PHP constants true, false, and null MUST be in lower case. --> - <rule ref="Generic.PHP.LowerCaseConstant"/> - - <!-- <rule ref="Squiz.Scope.MethodScope"/> --> - <rule ref="Squiz.WhiteSpace.ScopeKeywordSpacing"/> - - <!-- In the argument list, there MUST NOT be a space before each comma, and there MUST be one space after each comma. --> - <!-- - <rule ref="Squiz.Functions.FunctionDeclarationArgumentSpacing"> - <properties> - <property name="equalsSpacing" value="1"/> - </properties> - </rule> - <rule ref="Squiz.Functions.FunctionDeclarationArgumentSpacing.SpacingAfterHint"> - <severity>0</severity> - </rule> - --> - <rule ref="PEAR.WhiteSpace.ScopeClosingBrace"/> - -</ruleset>
--- a/vendor/sabre/vobject/tests/phpunit.xml Mon Oct 06 12:19:59 2025 -0400 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,21 +0,0 @@ -<phpunit - colors="true" - bootstrap="bootstrap.php" - convertErrorsToExceptions="true" - convertNoticesToExceptions="true" - convertWarningsToExceptions="true" - strict="true" - > - <testsuite name="Sabre\VObject"> - <directory>VObject/</directory> - </testsuite> - - <filter> - <whitelist addUncoveredFilesFromWhitelist="true"> - <directory suffix=".php">../lib/</directory> - <exclude> - <file>../lib/Sabre/VObject/includes.php</file> - </exclude> - </whitelist> - </filter> -</phpunit>
