mirror of
https://github.com/FH-Complete/FHC-Core.git
synced 2026-10-12 23:14:02 +00:00
243 lines
8.0 KiB
PHP
243 lines
8.0 KiB
PHP
<?php
|
|
/**
|
|
* Copyright (C) 2026 fhcomplete.org
|
|
*
|
|
* This program is free software: you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation, either version 3 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
*/
|
|
|
|
if (!defined('BASEPATH'))
|
|
exit('No direct script access allowed');
|
|
|
|
// require_once('../../include/ical.class.php');
|
|
|
|
class FreeBusyLib
|
|
{
|
|
private $_ci; // Code igniter instance
|
|
|
|
public function __construct()
|
|
{
|
|
$this->_ci =& get_instance();
|
|
|
|
$this->_ci->load->model("ressource/Zeitsperre_model", "ZeitsperreModel");
|
|
}
|
|
|
|
//------------------------------------------------------------------------------------------------------------------
|
|
// Public methods
|
|
|
|
public function getFreeBusy($url)
|
|
{
|
|
$fileStream = @fopen($url, "r");
|
|
if (!$fileStream)
|
|
return [];
|
|
|
|
$busyTimeslots = [];
|
|
$fileContent = file_get_contents($url);
|
|
if (mb_strpos($fileContent, "BEGIN:VFREEBUSY") !== false) {
|
|
$busyTimeslots = $this->parseFreeBusyFormat($fileContent);
|
|
} else {
|
|
$busyTimeslots = $this->parseConventionalFormat($fileContent);
|
|
}
|
|
|
|
return $busyTimeslots;
|
|
}
|
|
|
|
public function getDefaultInternalFreeBusy($uid)
|
|
{
|
|
$events = [];
|
|
|
|
$this->_ci->load->library('StundenplanLib');
|
|
|
|
$startDate = new DateTime();
|
|
$startDate = $startDate->format("Y-m-d");
|
|
$endDate = new DateTime();
|
|
$endDate->modify("+1 year");
|
|
$endDate = $endDate->format("Y-m-d");
|
|
|
|
$userEvents = getData($this->_ci->stundenplanlib->getEventsUser($startDate, $endDate, $uid));
|
|
if ($userEvents && count($userEvents)) {
|
|
$userEvents = array_map(
|
|
function ($event) {
|
|
return [
|
|
"start" => $event->datum . " " . $event->beginn,
|
|
"end" => $event->datum . " " . $event->ende,
|
|
];
|
|
},
|
|
$userEvents
|
|
);
|
|
$events = array_merge($events, $userEvents);
|
|
}
|
|
|
|
$userAbsences = getData($this->_ci->ZeitsperreModel->getZeitsperre($uid));
|
|
if ($userAbsences && count($userAbsences)) {
|
|
$today = new DateTime();
|
|
$today = $today->format("Y-m-d");
|
|
$userAbsences = array_filter(
|
|
$userAbsences,
|
|
function ($absence) use ($today) {
|
|
return $absence->bisdatum >= $today;
|
|
}
|
|
);
|
|
$userAbsences = array_map(
|
|
function ($absence) {
|
|
return [
|
|
"start" => $absence->vondatum . " 00:00:00",
|
|
"end" => $absence->bisdatum . " 23:59:00",
|
|
];
|
|
},
|
|
$userAbsences
|
|
);
|
|
$events = array_merge($events, $userAbsences);
|
|
}
|
|
|
|
return $events;
|
|
}
|
|
|
|
//------------------------------------------------------------------------------------------------------------------
|
|
// Private methods
|
|
|
|
private function parseConventionalFormat($fileContent)
|
|
{
|
|
$fileContentRows = explode("\n", $fileContent);
|
|
$fileContentRows = array_map(function ($row) {
|
|
return trim($row);
|
|
}, $fileContentRows);
|
|
|
|
$busyTimeslots = [];
|
|
$isParsingEvent = false;
|
|
$parsedEvent = ["start" => null, "end" => null];
|
|
$currentDateTime = new DateTime();
|
|
$currentDateTime = $currentDateTime->format("Y-m-d H:i:s");
|
|
|
|
foreach ($fileContentRows as $row) {
|
|
if (mb_strpos($row, "BEGIN:VEVENT") !== false) {
|
|
$isParsingEvent = true;
|
|
} else if (mb_strpos($row, "END:VEVENT") !== false) {
|
|
if (
|
|
$isParsingEvent &&
|
|
$parsedEvent["start"] &&
|
|
$parsedEvent["end"] &&
|
|
$parsedEvent["end"] > $currentDateTime
|
|
) {
|
|
$busyTimeslots[] = $parsedEvent;
|
|
}
|
|
|
|
$isParsingEvent = false;
|
|
$parsedEvent["start"] = null;
|
|
$parsedEvent["end"] = null;
|
|
} else if (mb_strpos($row, "DTSTART;VALUE=DATE") !== false) {
|
|
$startDateString = explode(":", $row)[1];
|
|
$start = substr($startDateString, 0, 4) . "-" . substr($startDateString, 4, 2) . "-" . substr($startDateString, 6, 2) . " 00:00:00";
|
|
$parsedEvent["start"] = $start;
|
|
} else if (mb_strpos($row, "DTSTART") !== false) {
|
|
$timestamp = explode(":", $row)[1];
|
|
|
|
if (mb_substr($timestamp, -1) === "Z") {
|
|
$timestamp = $this->convertTimestampToLocalTimezone($timestamp);
|
|
} else if (mb_strpos($row, "TZID=") !== false) {
|
|
$remainingString = explode("TZID=", $row)[1];
|
|
$remainingString = explode(":", $remainingString)[0];
|
|
$timezoneIdentifier = explode(";", $remainingString)[0];
|
|
$timestamp = $this->convertTimestampToLocalTimezone($timestamp, $timezoneIdentifier);
|
|
}
|
|
|
|
$startDate = substr($timestamp, 0, 4) . "-" . substr($timestamp, 4, 2) . "-" . substr($timestamp, 6, 2);
|
|
$startTime = substr($timestamp, 9, 2) . ":" . substr($timestamp, 11, 2) . ":" . substr($timestamp, 13, 2);
|
|
$parsedEvent["start"] = $startDate . " " . $startTime;
|
|
} else if (mb_strpos($row, "DTEND;VALUE=DATE") !== false) {
|
|
$endDateString = explode(":", $row)[1];
|
|
$end = substr($endDateString, 0, 4) . "-" . substr($endDateString, 4, 2) . "-" . substr($endDateString, 6, 2) . " 00:00:00";
|
|
$parsedEvent["end"] = $end;
|
|
} else if (mb_strpos($row, "DTEND") !== false) {
|
|
$timestamp = explode(":", $row)[1];
|
|
if (mb_substr($timestamp, -1) === "Z") {
|
|
$timestamp = $this->convertTimestampToLocalTimezone($timestamp);
|
|
} else if (mb_strpos($row, "TZID=") !== false) {
|
|
$remainingString = explode("TZID=", $row)[1];
|
|
$remainingString = explode(":", $remainingString)[0];
|
|
$timezoneIdentifier = explode(";", $remainingString)[0];
|
|
$timestamp = $this->convertTimestampToLocalTimezone($timestamp, $timezoneIdentifier);
|
|
}
|
|
|
|
$endDate = substr($timestamp, 0, 4) . "-" . substr($timestamp, 4, 2) . "-" . substr($timestamp, 6, 2);
|
|
$endTime = substr($timestamp, 9, 2) . ":" . substr($timestamp, 11, 2) . ":" . substr($timestamp, 13, 2);
|
|
$parsedEvent["end"] = $endDate . " " . $endTime;
|
|
}
|
|
}
|
|
|
|
return $busyTimeslots;
|
|
}
|
|
|
|
private function parseFreeBusyFormat($fileContent)
|
|
{
|
|
$fileContentRows = explode("\n", $fileContent);
|
|
$fileContentRows = array_map(function ($row) {
|
|
return trim($row);
|
|
}, $fileContentRows);
|
|
|
|
$busyTimeslots = [];
|
|
$currentDateTime = new DateTime();
|
|
$currentDateTime = $currentDateTime->format("Y-m-d H:i:s");
|
|
|
|
foreach ($fileContentRows as $row) {
|
|
if (
|
|
mb_strpos($row, "VFREEBUSY") !== false ||
|
|
mb_strpos($row, "FREEBUSY") === false ||
|
|
mb_strpos($row, "FBTYPE=FREE") !== false
|
|
)
|
|
continue;
|
|
|
|
$timestamps = explode(":", $row)[1];
|
|
$timestamps = explode(",", $timestamps);
|
|
foreach ($timestamps as $timestamp) {
|
|
$startEndTimestamps = explode("/", $timestamp);
|
|
|
|
$startTimestamp = $startEndTimestamps[0];
|
|
$endTimestamp = $startEndTimestamps[1];
|
|
|
|
if (mb_substr($startTimestamp, -1) === "Z") {
|
|
$startTimestamp = $this->convertTimestampToLocalTimezone($startTimestamp);
|
|
}
|
|
if (mb_substr($endTimestamp, -1) === "Z") {
|
|
$endTimestamp = $this->convertTimestampToLocalTimezone($endTimestamp);
|
|
}
|
|
|
|
$startDate = substr($startTimestamp, 0, 4) . "-" . substr($startTimestamp, 4, 2) . "-" . substr($startTimestamp, 6, 2);
|
|
$startTime = substr($startTimestamp, 9, 2) . ":" . substr($startTimestamp, 11, 2) . ":" . substr($startTimestamp, 13, 2);
|
|
$start = $startDate . " " . $startTime;
|
|
|
|
$endDate = substr($endTimestamp, 0, 4) . "-" . substr($endTimestamp, 4, 2) . "-" . substr($endTimestamp, 6, 2);
|
|
$endTime = substr($endTimestamp, 9, 2) . ":" . substr($endTimestamp, 11, 2) . ":" . substr($endTimestamp, 13, 2);
|
|
$end = $endDate . " " . $endTime;
|
|
|
|
if ($end < $currentDateTime)
|
|
continue;
|
|
|
|
$busyTimeslots[] = ["start" => $start, "end" => $end];
|
|
}
|
|
}
|
|
|
|
return $busyTimeslots;
|
|
}
|
|
|
|
private function convertTimestampToLocalTimezone($timestamp, $originalTimezoneIdentifier = "UTC")
|
|
{
|
|
$originalTimezone = new DateTimeZone($originalTimezoneIdentifier);
|
|
$localTimezone = new DateTimeZone("Europe/Vienna");
|
|
|
|
$date = new DateTime($timestamp, $originalTimezone);
|
|
$date->setTimezone($localTimezone);
|
|
return $date->format("Ymd\THis");
|
|
}
|
|
}
|