From b409fbb72591b43df7431e83e30d6c00ea633f21 Mon Sep 17 00:00:00 2001 From: Simon Rettberg Date: Thu, 5 Apr 2018 15:08:52 +0200 Subject: [locationinfo] Add exchange backend Closes #3170 --- .../coursebackend/coursebackend_exchange.inc.php | 242 +++++++++++++++++++++ .../locationinfo/inc/coursebackend/exchange.todo | 203 ----------------- 2 files changed, 242 insertions(+), 203 deletions(-) create mode 100755 modules-available/locationinfo/inc/coursebackend/coursebackend_exchange.inc.php delete mode 100755 modules-available/locationinfo/inc/coursebackend/exchange.todo (limited to 'modules-available/locationinfo/inc/coursebackend') diff --git a/modules-available/locationinfo/inc/coursebackend/coursebackend_exchange.inc.php b/modules-available/locationinfo/inc/coursebackend/coursebackend_exchange.inc.php new file mode 100755 index 00000000..a62ea6d5 --- /dev/null +++ b/modules-available/locationinfo/inc/coursebackend/coursebackend_exchange.inc.php @@ -0,0 +1,242 @@ +getClient(); + $request = new ResolveNamesType(); + $request->UnresolvedEntry = $this->username; + $request->ReturnFullContactData = false; + + try { + $response = $client->ResolveNames($request); + } catch (Exception $e) { + $this->error = $e->getMessage(); + return false; + } + + try { + if ($response->ResponseMessages->ResolveNamesResponseMessage[0]->ResponseCode === "NoError") { + $mailadress = $response->ResponseMessages->ResolveNamesResponseMessage[0]->ResolutionSet->Resolution[0]->Mailbox->EmailAddress; + return !empty($mailadress); + } + } catch (Exception $e) { + $this->error = $e->getMessage(); + } + return false; + } + + /** + * uses json to setCredentials, the json must follow the form given in + * getCredentials + * + * @param array $data assoc array with data required by backend + * @returns bool if the credentials were in the correct format + */ + public function setCredentialsInternal($data) + { + foreach (['username', 'password'] as $field) { + if (empty($data[$field])) { + $this->error = 'setCredentials: Missing field ' . $field; + return false; + } + } + + if (empty($data['serverAddress'])) { + $this->error = "No url is given"; + return false; + } + + $this->username = $data['username']; + $this->password = $data['password']; + + $this->serverAddress = $data['serverAddress']; + $this->clientVersion = $data['clientVersion']; + + $this->verifyHostname = $data['verifyHostname']; + $this->verifyCert = $data['verifyCert']; + + return true; + } + + /** + * @return int desired caching time of results, in seconds. 0 = no caching + */ + public function getCacheTime() + { + return 0; + } + + /** + * @return int age after which timetables are no longer refreshed. should be + * greater than CacheTime. + */ + public function getRefreshTime() + { + return 0; + } + + /** + * Internal version of fetch, to be overridden by subclasses. + * + * @param $roomIds array with local ID as key and serverId as value + * @return array a recursive array that uses the roomID as key + * and has the schedule array as value. A shedule array contains an array in this format: + * ["start"=>'JJJJ-MM-DD HH:MM:SS',"end"=>'JJJJ-MM-DD HH:MM:SS',"title"=>string] + */ + protected function fetchSchedulesInternal($requestedRoomIds) + { + $startDate = new DateTime('today 0:00'); + $endDate = new DateTime('+7 days 0:00'); + $client = $this->getClient(); + + $schedules = []; + foreach ($requestedRoomIds as $roomId) { + try { + $items = $this->findEventsForRoom($client, $startDate, $endDate, $roomId); + } catch (Exception $e) { + $this->error .= "Failed to search for events for room $roomId: '{$e->getMessage()}'\n"; + continue; + } + + // Iterate over the events that were found, printing some data for each. + foreach ($items as $item) { + $start = new DateTime($item->Start); + $end = new DateTime($item->End); + + $schedules[$roomId][] = array( + 'title' => $item->Subject, + 'start' => $start->format('Y-m-d') . "T" . $start->format('G:i:s'), + 'end' => $end->format('Y-m-d') . "T" . $end->format('G:i:s') + ); + } + } + return $schedules; + } + + /** + * @param \jamesiarmes\PhpEws\Client $client + * @param \DateTime $startDate + * @param \DateTime $endDate + * @param string $roomAddress + * @return \jamesiarmes\PhpEws\Type\CalendarItemType[] + */ + public function findEventsForRoom($client, $startDate, $endDate, $roomAddress) + { + $request = new FindItemType(); + $request->Traversal = ItemQueryTraversalType::SHALLOW; + $request->ItemShape = new ItemResponseShapeType(); + $request->ItemShape->BaseShape = DefaultShapeNamesType::ALL_PROPERTIES; + + $request->CalendarView = new CalendarViewType(); + $request->CalendarView->StartDate = $startDate->format('c'); + $request->CalendarView->EndDate = $endDate->format('c'); + $folderId = new DistinguishedFolderIdType(); + $folderId->Id = DistinguishedFolderIdNameType::CALENDAR; + $folderId->Mailbox = new EmailAddressType(); + $folderId->Mailbox->EmailAddress = $roomAddress; + $request->ParentFolderIds->DistinguishedFolderId[] = $folderId; + $response = $client->FindItem($request); + $response_messages = $response->ResponseMessages->FindItemResponseMessage; + + $items = []; + foreach ($response_messages as $response_message) { + // Make sure the request succeeded. + if ($response_message->ResponseClass !== ResponseClassType::SUCCESS) { + $code = $response_message->ResponseCode; + $message = $response_message->MessageText; + $this->error .= "Failed to search for events for room $roomAddress: '$code: $message'\n"; + continue; + } + $items = array_merge($items, $response_message->RootFolder->Items->CalendarItem); + } + return $items; + } + + /** + * @return \jamesiarmes\PhpEws\Client + */ + public function getClient() + { + $client = new Client($this->serverAddress, $this->username, $this->password, $this->clientVersion); + $client->setTimezone($this->timezone); + $client->setCurlOptions(array( + CURLOPT_SSL_VERIFYPEER => $this->verifyHostname, + CURLOPT_SSL_VERIFYHOST => $this->verifyCert + )); + + return $client; + } + +} diff --git a/modules-available/locationinfo/inc/coursebackend/exchange.todo b/modules-available/locationinfo/inc/coursebackend/exchange.todo deleted file mode 100755 index 538f7382..00000000 --- a/modules-available/locationinfo/inc/coursebackend/exchange.todo +++ /dev/null @@ -1,203 +0,0 @@ -getClient(); - $request = new ResolveNamesType(); - $request->UnresolvedEntry = $this->username; - $request->ReturnFullContactData = false; - - try { - $response = $client->ResolveNames($request); - } catch (Exception $e) { - error_log("There was an error"); - error_log($e->getMessage()); - return false; - } - - if ($response->ResponseMessages->ResolveNamesResponseMessage[0]->ResponseCode == "NoError") { - $mailadress = $response->ResponseMessages->ResolveNamesResponseMessage[0]->ResolutionSet->Resolution[0]->Mailbox->EmailAddress; - return !empty($mailadress); - } - return false; - } - - /** - * uses json to setCredentials, the json must follow the form given in - * getCredentials - * - * @param array $data assoc array with data required by backend - * @returns bool if the credentials were in the correct format - */ - public function setCredentialsInternal($data) { - foreach (['username', 'password'] as $field) { - if (empty($data[$field])) { - $this->error = 'setCredentials: Missing field ' . $field; - return false; - } - } - - if (empty($data['baseUrl'])) { - $this->error = "No url is given"; - return false; - } - - $this->username = $data['username']; - $this->password = $data['password']; - - $this->baseUrl = $data['baseUrl']; - $this->client_version = $data['client_version']; - - $this->verifyHostname = $data['verifyHostname']; - $this->verifyCert = $data['verifyCert']; - - return true; - } - - /** - * @return int desired caching time of results, in seconds. 0 = no caching - */ - public function getCacheTime() { - return 0; - } - - /** - * @return int age after which timetables are no longer refreshed should be - * greater then CacheTime - */ - public function getRefreshTime() { - return 0; - } - - /** - * Internal version of fetch, to be overridden by subclasses. - * - * @param $roomIds array with local ID as key and serverId as value - * @return array a recursive array that uses the roomID as key - * and has the schedule array as value. A shedule array contains an array in this format: - * ["start"=>'JJJJ-MM-DD HH:MM:SS',"end"=>'JJJJ-MM-DD HH:MM:SS',"title"=>string] - */ - protected function fetchSchedulesInternal($requestedRoomIds) { - $startDate = new DateTime('today 0:00'); - $endDate = new DateTime('+7 days 0:00'); - $client = $this->getClient(); - - $schedules = []; - foreach ($requestedRoomIds as $roomId) { - $items = $this->findEventsForRoom($client, $startDate, $endDate, $roomId); - - // Iterate over the events that were found, printing some data for each. - foreach ($items as $item) { - $start = new DateTime($item->Start); - $end = new DateTime($item->End); - - $schedules[$roomId][] = array( - 'title' => $item->Subject, - 'start' => $start->format('Y-m-d') . "T" . $start->format('G:i:s'), - 'end' => $end->format('Y-m-d') . "T" . $end->format('G:i:s') - ); - } - } - return $schedules; - } - - public function findEventsForRoom($client, $start_date, $end_date, $email_room) { - $request = new FindItemType(); - $request->Traversal = ItemQueryTraversalType::SHALLOW; - $request->ItemShape = new ItemResponseShapeType(); - $request->ItemShape->BaseShape = DefaultShapeNamesType::ALL_PROPERTIES; - - $request->CalendarView = new CalendarViewType(); - $request->CalendarView->StartDate = $start_date->format('c'); - $request->CalendarView->EndDate = $end_date->format('c'); - $folder_id = new DistinguishedFolderIdType(); - $folder_id->Id = DistinguishedFolderIdNameType::CALENDAR; - $folder_id->Mailbox = new EmailAddressType(); - $folder_id->Mailbox->EmailAddress = $email_room; - $request->ParentFolderIds->DistinguishedFolderId[] = $folder_id; - $response = $client->FindItem($request); - $response_messages = $response->ResponseMessages->FindItemResponseMessage; - - $items = []; - foreach ($response_messages as $response_message) { - // Make sure the request succeeded. - if ($response_message->ResponseClass != ResponseClassType::SUCCESS) { - $code = $response_message->ResponseCode; - $message = $response_message->MessageText; - error_log("Failed to search for events with \"$code: $message\"\n"); - continue; - } - $items = $response_message->RootFolder->Items->CalendarItem; - } - return $items; - } - - public function getClient() { - $client = new Client($this->baseUrl, $this->username, $this->password, $this->client_version); - $client->setTimezone($this->timezone); - $client->setCurlOptions(array( - CURLOPT_SSL_VERIFYPEER => $this->verifyHostname, - CURLOPT_SSL_VERIFYHOST => $this->verifyCert - )); - - return $client; - } - - function var_error_log($object = null) { - ob_start(); // start buffer capture - var_dump($object); // dump the values - $contents = ob_get_contents(); // put the buffer into a variable - ob_end_clean(); // end capture - error_log($contents); // log contents of the result of var_dump( $object ) - } -} -?> -- cgit v1.2.3-55-g7522 From 476d7ceab912113c8feb657478c05154aeb3f26f Mon Sep 17 00:00:00 2001 From: Simon Rettberg Date: Wed, 18 Apr 2018 12:01:01 +0200 Subject: [locationinfo] hisinone: Query relevant days only, not whole year/semester Speed up queries significantly by not going through all the courses for the whole year, but just query those that take place in the next seven days. We also reuse the curl handle now for some additional speedup. --- .../coursebackend/coursebackend_hisinone.inc.php | 84 ++++++++++++---------- 1 file changed, 46 insertions(+), 38 deletions(-) (limited to 'modules-available/locationinfo/inc/coursebackend') diff --git a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php index 59bd9dc8..558f5cd0 100644 --- a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php +++ b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php @@ -8,6 +8,10 @@ class CourseBackend_HisInOne extends CourseBackend private $location; private $verifyHostname = true; private $verifyCert = true; + /** + * @var bool|resource + */ + private $curlHandle = false; public function setCredentialsInternal($data) @@ -27,7 +31,10 @@ class CourseBackend_HisInOne extends CourseBackend } $this->error = false; - $this->username = $data['username'] . "\t" . $data['role']; + $this->username = $data['username']; + if (!empty($data['role'])) { + $this->username .= "\t" . $data['role']; + } $this->password = $data['password']; $this->open = $data['open'] !== 'CourseService'; $url = preg_replace('#(/+qisserver(/+services\d+(/+OpenCourseService)?)?)?\W*$#i', '', $data['baseUrl']); @@ -60,7 +67,7 @@ class CourseBackend_HisInOne extends CourseBackend if (empty($this->location)) { $this->error = "Credentials are not set"; } else { - $this->findUnit(123456789, true); + $this->findUnit(123456789, date('Y-m-d'), true); } return $this->error === false; } @@ -70,18 +77,8 @@ class CourseBackend_HisInOne extends CourseBackend * @param bool $connectionCheckOnly true will only check if no soapError is returned, return value will be empty * @return array|bool if successful an array with the event ids that take place in the room */ - public function findUnit($roomId, $connectionCheckOnly = false) + public function findUnit($roomId, $day, $connectionCheckOnly = false) { - $termYear = date('Y'); - $termType1 = date('n'); - if ($termType1 > 3 && $termType1 < 10) { - $termType = 2; - } elseif ($termType1 > 10) { - $termType = 1; - $termYear = $termYear + 1; - } else { - $termType = 1; - } $doc = new DOMDocument('1.0', 'utf-8'); $doc->formatOutput = true; $envelope = $doc->createElementNS('http://schemas.xmlsoap.org/soap/envelope/', 'SOAP-ENV:Envelope'); @@ -90,18 +87,15 @@ class CourseBackend_HisInOne extends CourseBackend $envelope->setAttributeNS('http://www.w3.org/2000/xmlns/', 'xmlns:ns1', 'http://www.his.de/ws/OpenCourseService'); } else { $envelope->setAttributeNS('http://www.w3.org/2000/xmlns/', 'xmlns:ns1', 'http://www.his.de/ws/CourseService'); - $header = $this->getHeader($doc); - $envelope->appendChild($header); } + $header = $this->getHeader($doc); + $envelope->appendChild($header); //Body of the request $body = $doc->createElement('SOAP-ENV:Body'); $envelope->appendChild($body); $findUnit = $doc->createElement('ns1:findUnit'); $body->appendChild($findUnit); - $findUnit->appendChild($doc->createElement('termYear', $termYear)); - if ($termType1 != 3 && $termType1 != 10) { - $findUnit->appendChild($doc->createElement('termTypeValueId', $termType)); - } + $findUnit->appendChild($doc->createElement('ns1:individualDatesExecutionDate', $day)); $findUnit->appendChild($doc->createElement('ns1:roomId', $roomId)); $soap_request = $doc->saveXML(); @@ -146,7 +140,7 @@ class CourseBackend_HisInOne extends CourseBackend $idList = $this->getArrayPath($idSubDoc, $subpath); if ($idList === false) { $this->error = 'Cannot find ' . $subpath . ' after ' . $path; - @file_put_contents('/tmp/findUnit-2.' . $roomId . '.' . microtime(true), print_r($idSubDoc, true)); + @file_put_contents('/tmp/bwlp-findUnit-2.' . $roomId . '.' . microtime(true), print_r($idSubDoc, true)); } return $idList; } @@ -188,7 +182,9 @@ class CourseBackend_HisInOne extends CourseBackend "Content-length: " . strlen($request), ); - $soap_do = curl_init(); + if ($this->curlHandle === false) { + $this->curlHandle = curl_init(); + } $options = array( CURLOPT_RETURNTRANSFER => true, @@ -200,17 +196,16 @@ class CourseBackend_HisInOne extends CourseBackend CURLOPT_HTTPHEADER => $header, ); - curl_setopt_array($soap_do, $options); + curl_setopt_array($this->curlHandle, $options); - $output = curl_exec($soap_do); + $output = curl_exec($this->curlHandle); if ($output === false) { - $this->error = 'Curl error: ' . curl_error($soap_do); + $this->error = 'Curl error: ' . curl_error($this->curlHandle); } else { $this->error = false; ///Operation completed successfully } - curl_close($soap_do); return $output; } @@ -236,21 +231,28 @@ class CourseBackend_HisInOne extends CourseBackend if (empty($requestedRoomIds)) { return array(); } + $currentWeek = $this->getCurrentWeekDates(); $tTables = []; //get all eventIDs in a given room $eventIds = []; foreach ($requestedRoomIds as $roomId) { - $roomEventIds = $this->findUnit($roomId); - if ($roomEventIds === false) { - if ($this->error !== false) { - error_log('Cannot findUnit(' . $roomId . '): ' . $this->error); - $this->error = false; + $ok = false; + foreach ($currentWeek as $day) { + $roomEventIds = $this->findUnit($roomId, $day, false); + if ($roomEventIds === false) { + if ($this->error !== false) { + error_log('Cannot findUnit(' . $roomId . '): ' . $this->error); + $this->error = false; + } + // TODO: Error gets swallowed + continue; } - // TODO: Error gets swallowed - continue; + $ok = true; + $eventIds = array_merge($eventIds, $roomEventIds); + } + if ($ok) { + $tTables[$roomId] = []; } - $tTables[$roomId] = []; - $eventIds = array_merge($eventIds, $roomEventIds); } $eventIds = array_unique($eventIds); if (empty($eventIds)) { @@ -268,7 +270,6 @@ class CourseBackend_HisInOne extends CourseBackend } $eventDetails = array_merge($eventDetails, $event); } - $currentWeek = $this->getCurrentWeekDates(); $name = false; foreach ($eventDetails as $event) { foreach (array('/hisdefaulttext', @@ -323,9 +324,9 @@ class CourseBackend_HisInOne extends CourseBackend $envelope->setAttributeNS('http://www.w3.org/2000/xmlns/', 'xmlns:ns1', 'http://www.his.de/ws/OpenCourseService'); } else { $envelope->setAttributeNS('http://www.w3.org/2000/xmlns/', 'xmlns:ns1', 'http://www.his.de/ws/CourseService'); - $header = $this->getHeader($doc); - $envelope->appendChild($header); } + $header = $this->getHeader($doc); + $envelope->appendChild($header); //body of the request $body = $doc->createElement('SOAP-ENV:Body'); $envelope->appendChild($body); @@ -359,10 +360,17 @@ class CourseBackend_HisInOne extends CourseBackend { $returnValue = array(); $startDate = time(); - for ($i = 0; $i <= 7; $i++) { + for ($i = 0; $i < 7; $i++) { $returnValue[] = date('Y-m-d', strtotime("+{$i} day 12:00", $startDate)); } return $returnValue; } + public function __destruct() + { + if ($this->curlHandle !== false) { + curl_close($this->curlHandle); + } + } + } -- cgit v1.2.3-55-g7522 From 1c18aa67abaf179602458909e50d983a44ee2dc7 Mon Sep 17 00:00:00 2001 From: Simon Rettberg Date: Wed, 18 Apr 2018 12:03:52 +0200 Subject: [locationinfo] davinchi: Reuse curl handle --- .../coursebackend/coursebackend_davinci.inc.php | 22 +++++++++++++++++----- 1 file changed, 17 insertions(+), 5 deletions(-) (limited to 'modules-available/locationinfo/inc/coursebackend') diff --git a/modules-available/locationinfo/inc/coursebackend/coursebackend_davinci.inc.php b/modules-available/locationinfo/inc/coursebackend/coursebackend_davinci.inc.php index 8843e372..ed3d7ec2 100644 --- a/modules-available/locationinfo/inc/coursebackend/coursebackend_davinci.inc.php +++ b/modules-available/locationinfo/inc/coursebackend/coursebackend_davinci.inc.php @@ -6,6 +6,10 @@ class CourseBackend_Davinci extends CourseBackend private $location; private $verifyHostname = true; private $verifyCert = true; + /** + * @var bool|resource + */ + private $curlHandle = false; public function setCredentialsInternal($data) { @@ -69,7 +73,9 @@ class CourseBackend_Davinci extends CourseBackend { $url = $this->location . "content=xml&type=room&name=" . urlencode($roomId) . "&startdate=" . $startDate->format('d.m.Y') . "&enddate=" . $endDate->format('d.m.Y'); - $ch = curl_init(); + if ($this->curlHandle === false) { + $this->curlHandle = curl_init(); + } $options = array( CURLOPT_RETURNTRANSFER => true, CURLOPT_FOLLOWLOCATION => true, @@ -78,16 +84,15 @@ class CourseBackend_Davinci extends CourseBackend CURLOPT_URL => $url, ); - curl_setopt_array($ch, $options); - $output = curl_exec($ch); + curl_setopt_array($this->curlHandle, $options); + $output = curl_exec($this->curlHandle); if ($output === false) { - $this->error = 'Curl error: ' . curl_error($ch); + $this->error = 'Curl error: ' . curl_error($this->curlHandle); return false; } else { $this->error = false; ///Operation completed successfully } - curl_close($ch); return $output; } @@ -142,4 +147,11 @@ class CourseBackend_Davinci extends CourseBackend } return $schedules; } + + public function __destruct() + { + if ($this->curlHandle !== false) { + curl_close($this->curlHandle); + } + } } -- cgit v1.2.3-55-g7522 From cd092274b88599449902f480f35291768be6e99e Mon Sep 17 00:00:00 2001 From: Simon Rettberg Date: Tue, 7 Aug 2018 16:54:01 +0200 Subject: [inc/User] Fix access to Page if class is not loaded --- inc/user.inc.php | 11 ++++- lang/pt/flag.png | Bin 1115 -> 0 bytes lang/pt/name.txt | 1 - modules-available/exams/lang/de/template-tags.json | 2 +- modules-available/exams/lang/en/template-tags.json | 2 +- .../coursebackend/coursebackend_hisinone.inc.php | 48 +++++++++++++-------- .../locationinfo/lang/de/template-tags.json | 2 +- .../locationinfo/lang/en/template-tags.json | 2 +- 8 files changed, 43 insertions(+), 25 deletions(-) delete mode 100644 lang/pt/flag.png delete mode 100644 lang/pt/name.txt (limited to 'modules-available/locationinfo/inc/coursebackend') diff --git a/inc/user.inc.php b/inc/user.inc.php index 2571c61c..20e8cd3d 100644 --- a/inc/user.inc.php +++ b/inc/user.inc.php @@ -34,8 +34,15 @@ class User if ($permission{0} === '.') { $permission = substr($permission, 1); } else { - $module = Page::getModule(); - $permission = $module ? $module->getIdentifier() . "." . $permission : $permission; + if (class_exists('Page')) { + $module = Page::getModule(); + if ($module !== false) { + $module = $module->getIdentifier(); + } + } else { + $module = strtolower(Request::any('do')); + } + $permission = $module ? $module . "." . $permission : $permission; } return PermissionUtil::userHasPermission(self::$user['userid'], $permission, $locationid); } diff --git a/lang/pt/flag.png b/lang/pt/flag.png deleted file mode 100644 index 78c57dea..00000000 Binary files a/lang/pt/flag.png and /dev/null differ diff --git a/lang/pt/name.txt b/lang/pt/name.txt deleted file mode 100644 index 811b10b4..00000000 --- a/lang/pt/name.txt +++ /dev/null @@ -1 +0,0 @@ -Português \ No newline at end of file diff --git a/modules-available/exams/lang/de/template-tags.json b/modules-available/exams/lang/de/template-tags.json index 8bf37143..1dd51374 100644 --- a/modules-available/exams/lang/de/template-tags.json +++ b/modules-available/exams/lang/de/template-tags.json @@ -29,7 +29,7 @@ "lang_headingMain": "bwLehrpool Pr\u00fcfungsmodus", "lang_id": "ID", "lang_lectureName": "Veranstaltungsname", - "lang_lectureOutOfRange": "Achtung: Start- bzw. Endzeitpunkt der Veranstaltung liegen au\u00dferhalb des oben angegebenen Zeitraums", + "lang_lectureOutOfRange": "Achtung: Der oben angegebene Zeitraum ist k\u00fcrzer als die Dauer der Veranstaltung", "lang_location": "Raum\/Ort", "lang_locationInfo": "W\u00e4hlen Sie hier die R\u00e4ume und Orte aus, die w\u00e4hrend des unten ausgew\u00e4hlten Zeitraums in den Pr\u00fcfungsmodus versetzt werden. Wenn sie hier keine Auswahl treffen, werden alle R\u00e4ume in den Pr\u00fcfungsmodus versetzt.", "lang_locations": "R\u00e4ume\/Orte", diff --git a/modules-available/exams/lang/en/template-tags.json b/modules-available/exams/lang/en/template-tags.json index af87bb01..23266154 100644 --- a/modules-available/exams/lang/en/template-tags.json +++ b/modules-available/exams/lang/en/template-tags.json @@ -29,7 +29,7 @@ "lang_headingMain": "bwLehrpool Exam Mode", "lang_id": "ID", "lang_lectureName": "Lecture name", - "lang_lectureOutOfRange": "Hint: Start or end date of given lecture lies outside of exam period given above", + "lang_lectureOutOfRange": "Hint: The exam period given above is shorter than the duration of the given lecture", "lang_location": "Room\/Location", "lang_locationInfo": "Select the rooms and locations you want to enable the exam mode in. Selecting nothing at all means that all clients will boot into exam mode during the given time period.", "lang_locations": "Rooms\/Locations", diff --git a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php index 558f5cd0..3b26e625 100644 --- a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php +++ b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php @@ -274,8 +274,7 @@ class CourseBackend_HisInOne extends CourseBackend foreach ($eventDetails as $event) { foreach (array('/hisdefaulttext', '/hisshorttext', - '/hisshortcomment', - '/hisplanelements/hisplanelement/hisdefaulttext') as $path) { + '/hisshortcomment') as $path) { $name = $this->getArrayPath($event, $path); if (!empty($name) && !empty($name[0])) break; @@ -284,25 +283,38 @@ class CourseBackend_HisInOne extends CourseBackend if ($name === false) { $name = ['???']; } - $unitPlannedDates = $this->getArrayPath($event, - '/hisplanelements/hisplanelement/hisplannedDates/hisplannedDate/hisindividualDates/hisindividualDate'); - if ($unitPlannedDates === false) { - $this->error = 'Cannot find ./hisplanelements/hisplanelement/hisplannedDates/hisplannedDate/hisindividualDates/hisindividualDate'; - error_log('Cannot find ./hisplanelements/hisplanelement/hisplannedDates/hisplannedDate/hisindividualDates/hisindividualDate'); + $planElements = $this->getArrayPath($event, '/hisplanelements/hisplanelement'); + if ($planElements === false) { + $this->error = 'Cannot find ./hisplanelements/hisplanelement'; + error_log('Cannot find ./hisplanelements/hisplanelement'); error_log(print_r($event, true)); continue; } - foreach ($unitPlannedDates as $plannedDate) { - $eventRoomId = $this->getArrayPath($plannedDate, '/hisroomId')[0]; - $eventDate = $this->getArrayPath($plannedDate, '/hisexecutiondate')[0]; - if (in_array($eventRoomId, $requestedRoomIds) && in_array($eventDate, $currentWeek)) { - $startTime = $this->getArrayPath($plannedDate, '/hisstarttime')[0]; - $endTime = $this->getArrayPath($plannedDate, '/hisendtime')[0]; - $tTables[$eventRoomId][] = array( - 'title' => $name[0], - 'start' => $eventDate . "T" . $startTime, - 'end' => $eventDate . "T" . $endTime - ); + foreach ($planElements as $planElement) { + $unitPlannedDates = $this->getArrayPath($planElement, + '/hisplannedDates/hisplannedDate/hisindividualDates/hisindividualDate'); + if ($unitPlannedDates === false) { + $this->error = 'Cannot find ./hisplannedDates/hisplannedDate/hisindividualDates/hisindividualDate'; + error_log('Cannot find ./hisplannedDates/hisplannedDate/hisindividualDates/hisindividualDate'); + error_log(print_r($planElement, true)); + continue; + } + $localName = $this->getArrayPath($planElement, '/hisdefaulttext'); + if ($localName === false || empty($localName[0])) { + $localName = $name; + } + foreach ($unitPlannedDates as $plannedDate) { + $eventRoomId = $this->getArrayPath($plannedDate, '/hisroomId')[0]; + $eventDate = $this->getArrayPath($plannedDate, '/hisexecutiondate')[0]; + if (in_array($eventRoomId, $requestedRoomIds) && in_array($eventDate, $currentWeek)) { + $startTime = $this->getArrayPath($plannedDate, '/hisstarttime')[0]; + $endTime = $this->getArrayPath($plannedDate, '/hisendtime')[0]; + $tTables[$eventRoomId][] = array( + 'title' => $localName[0], + 'start' => $eventDate . "T" . $startTime, + 'end' => $eventDate . "T" . $endTime + ); + } } } } diff --git a/modules-available/locationinfo/lang/de/template-tags.json b/modules-available/locationinfo/lang/de/template-tags.json index bcdf7148..b51c420b 100644 --- a/modules-available/locationinfo/lang/de/template-tags.json +++ b/modules-available/locationinfo/lang/de/template-tags.json @@ -76,7 +76,7 @@ "lang_remoteSchedule": "Abruf Belegungsplan", "lang_room": "Raum", "lang_roomId": "Raum ID", - "lang_roomIdTooltip": "Die Raum ID, die der Server ben\u00f6tigt, um Kalenderdaten abzurufen", + "lang_roomIdTooltip": "Die Raum ID, die der Server ben\u00f6tigt, um Kalenderdaten abzurufen (bei Exchange die Postfachadresse)", "lang_roomupdateTooltip": "Zeit nach der die PCs aktualisiert werden (in Sekunden)", "lang_rotation": "Rotation", "lang_rotation0": "0\u00b0", diff --git a/modules-available/locationinfo/lang/en/template-tags.json b/modules-available/locationinfo/lang/en/template-tags.json index 558ddff0..f041dc0a 100644 --- a/modules-available/locationinfo/lang/en/template-tags.json +++ b/modules-available/locationinfo/lang/en/template-tags.json @@ -76,7 +76,7 @@ "lang_remoteSchedule": "Time table retrieval", "lang_room": "Room", "lang_roomId": "Room ID", - "lang_roomIdTooltip": "The ID of the room the server needs, for querying the calendar data", + "lang_roomIdTooltip": "The ID of the room the server needs, for querying the calendar data (when using exchange the room mailbox)", "lang_roomupdateTooltip": "Time the PCs in the room gets updated (in seconds)", "lang_rotation": "Rotation", "lang_rotation0": "0\u00b0", -- cgit v1.2.3-55-g7522 From acd0f96696dc5c7d581902186f913fb3dff5302d Mon Sep 17 00:00:00 2001 From: Simon Rettberg Date: Mon, 3 Dec 2018 11:55:51 +0100 Subject: [locationinfo] HiS: Check if event has any planned dates --- .../locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php | 2 ++ 1 file changed, 2 insertions(+) (limited to 'modules-available/locationinfo/inc/coursebackend') diff --git a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php index 3b26e625..22b1d8fb 100644 --- a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php +++ b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php @@ -291,6 +291,8 @@ class CourseBackend_HisInOne extends CourseBackend continue; } foreach ($planElements as $planElement) { + if (empty($planElement['hisplannedDates'])) + continue; $unitPlannedDates = $this->getArrayPath($planElement, '/hisplannedDates/hisplannedDate/hisindividualDates/hisindividualDate'); if ($unitPlannedDates === false) { -- cgit v1.2.3-55-g7522 From f538335087e18ad5950eee0ec1c9654fff5addc5 Mon Sep 17 00:00:00 2001 From: Simon Rettberg Date: Tue, 29 Jan 2019 09:22:28 +0100 Subject: [locationinfo] HisInOne: Properly handle multiple plannedDates If a course has been running for several semesters, older plannedDate entries tend to have no individualDate entries. Ignore those and don't error_log about it. --- .../locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'modules-available/locationinfo/inc/coursebackend') diff --git a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php index 22b1d8fb..c71623b3 100644 --- a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php +++ b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php @@ -271,6 +271,7 @@ class CourseBackend_HisInOne extends CourseBackend $eventDetails = array_merge($eventDetails, $event); } $name = false; + $now = time(); foreach ($eventDetails as $event) { foreach (array('/hisdefaulttext', '/hisshorttext', @@ -293,6 +294,12 @@ class CourseBackend_HisInOne extends CourseBackend foreach ($planElements as $planElement) { if (empty($planElement['hisplannedDates'])) continue; + $checkDate = $this->getArrayPath($planElement, '/hisplannedDates/hisplannedDate/hisenddate'); + if (!empty($checkDate) && strtotime($checkDate[0]) + 86400 < $now) + continue; // Course ended + $checkDate = $this->getArrayPath($planElement, '/hisplannedDates/hisplannedDate/hisstartdate'); + if (!empty($checkDate) && strtotime($checkDate[0]) - 86400 > $now) + continue; // Course didn't start yet $unitPlannedDates = $this->getArrayPath($planElement, '/hisplannedDates/hisplannedDate/hisindividualDates/hisindividualDate'); if ($unitPlannedDates === false) { -- cgit v1.2.3-55-g7522 From d6da57101c3e4b54d25f65978594bbdec11205f8 Mon Sep 17 00:00:00 2001 From: Simon Rettberg Date: Tue, 19 Feb 2019 12:35:03 +0100 Subject: [locationinfo] Fix events not showing HISinOne start and end dates are not reliable - ignore and check individual planned dates. --- .../locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'modules-available/locationinfo/inc/coursebackend') diff --git a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php index c71623b3..2ffb9f41 100644 --- a/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php +++ b/modules-available/locationinfo/inc/coursebackend/coursebackend_hisinone.inc.php @@ -294,12 +294,17 @@ class CourseBackend_HisInOne extends CourseBackend foreach ($planElements as $planElement) { if (empty($planElement['hisplannedDates'])) continue; + // Do not use -- is set improperly for some courses :-( + /* $checkDate = $this->getArrayPath($planElement, '/hisplannedDates/hisplannedDate/hisenddate'); if (!empty($checkDate) && strtotime($checkDate[0]) + 86400 < $now) continue; // Course ended $checkDate = $this->getArrayPath($planElement, '/hisplannedDates/hisplannedDate/hisstartdate'); if (!empty($checkDate) && strtotime($checkDate[0]) - 86400 > $now) continue; // Course didn't start yet + */ + $cancelled = $this->getArrayPath($planElement, '/hiscancelled'); + $cancelled = $cancelled !== false && is_array($cancelled) && ($cancelled[0] > 0 || strtolower($cancelled[0]) === 'true'); $unitPlannedDates = $this->getArrayPath($planElement, '/hisplannedDates/hisplannedDate/hisindividualDates/hisindividualDate'); if ($unitPlannedDates === false) { @@ -321,7 +326,8 @@ class CourseBackend_HisInOne extends CourseBackend $tTables[$eventRoomId][] = array( 'title' => $localName[0], 'start' => $eventDate . "T" . $startTime, - 'end' => $eventDate . "T" . $endTime + 'end' => $eventDate . "T" . $endTime, + 'cancelled' => $cancelled, ); } } -- cgit v1.2.3-55-g7522