You are here

public function RlHelper::__construct in Recurring Dates Field 3.0.x

Same name and namespace in other branches
  1. 8.2 src/Rl/RlHelper.php \Drupal\date_recur\Rl\RlHelper::__construct()
  2. 3.x src/Rl/RlHelper.php \Drupal\date_recur\Rl\RlHelper::__construct()
  3. 3.1.x src/Rl/RlHelper.php \Drupal\date_recur\Rl\RlHelper::__construct()

Constructor for DateRecurHelper.

Parameters

string $string: The repeat rule.

\DateTimeInterface $dtStart: The initial occurrence start date.

\DateTimeInterface|null $dtStartEnd: The initial occurrence end date, or NULL to use start date.

File

src/Rl/RlHelper.php, line 54

Class

RlHelper
Helper for recurring rules implemented with rlanvin/rrule.

Namespace

Drupal\date_recur\Rl

Code

public function __construct(string $string, \DateTimeInterface $dtStart, ?\DateTimeInterface $dtStartEnd = NULL) {
  $dtStartEnd = $dtStartEnd ?? clone $dtStart;
  $this->recurDiff = $dtStart
    ->diff($dtStartEnd);
  $this->timeZone = $dtStart
    ->getTimezone();

  // Ensure the string is prefixed with RRULE if not multiline.
  if (strpos($string, "\n") === FALSE && strpos($string, 'RRULE:') !== 0) {
    $string = "RRULE:{$string}";
  }
  $parts = [
    'RRULE' => [],
    'RDATE' => [],
    'EXRULE' => [],
    'EXDATE' => [],
  ];
  $lines = explode("\n", $string);
  foreach ($lines as $n => $line) {
    $line = trim($line);
    if (FALSE === strpos($line, ':')) {
      throw new DateRecurHelperArgumentException(sprintf('Multiline RRULE must be prefixed with either: RRULE, EXDATE, EXRULE, or RDATE. Missing for line %s', $n + 1));
    }
    [
      $part,
      $partValue,
    ] = explode(':', $line, 2);
    if (!isset($parts[$part])) {
      throw new DateRecurHelperArgumentException("Unsupported line: " . $part);
    }
    $parts[$part][] = $partValue;
  }
  if (($count = count($parts['RRULE'])) !== 1) {
    throw new DateRecurHelperArgumentException(sprintf('One RRULE must be provided. %d provided.', $count));
  }
  $this->set = new RSet();
  foreach ($parts as $type => $values) {
    foreach ($values as $value) {
      switch ($type) {
        case 'RRULE':
          $this->set
            ->addRRule(new RRule($value, $dtStart));
          break;
        case 'RDATE':
          $dates = RfcParser::parseRDate('RDATE:' . $value);
          array_walk($dates, function (\DateTimeInterface $value) : void {
            $this->set
              ->addDate($value);
          });
          break;
        case 'EXDATE':
          $dates = RfcParser::parseExDate('EXDATE:' . $value);
          array_walk($dates, function (\DateTimeInterface $value) : void {
            $this->set
              ->addExDate($value);
          });
          break;
        case 'EXRULE':
          $this->set
            ->addExRule($value);
      }
    }
  }
}