Implemented cache

This commit is contained in:
PMKuipers 2024-03-08 09:16:19 +01:00
parent f1a994880d
commit 7a36615a76
11 changed files with 224 additions and 79 deletions

View File

@ -1,3 +1,3 @@
define("filter_bibleversesnwt/filter_bibleversesnwt",["exports","core/ajax","core/modal","core/modal_factory","core/modal_events","core/notification"],(function(_exports,_ajax,_modal,_modal_factory,_modal_events,_notification){function _interopRequireDefault(obj){return obj&&obj.__esModule?obj:{default:obj}}function bible_link(event){const target=event.target,info=JSON.parse(target.getAttribute("data-verseinfo")),bibleblock_heading=document.querySelector("#block_bibleblock_heading"),bibleblock_quote=document.querySelector("#block_bibleblock_content");return bibleblock_quote&&(bibleblock_heading&&(bibleblock_heading.innerHTML=""),bibleblock_quote.innerHTML='<div class="spinner-border text-info"></div>'),(0,_ajax.call)([{methodname:"filter_bibleversesnwt_get_biblequote",args:{lang:info.lang,book:info.book,ch:info.ch,verse:info.verse,book_end:info.book,ch_end:info.ch,verse_end:info.verse_end}}])[0].then((quote=>{var modalconfig;console.info("Got bible quote",quote),bibleblock_quote?(console.info("Attempting to place in verses block",bibleblock_heading,bibleblock_quote),bibleblock_heading&&(bibleblock_heading.innerHTML=quote.heading),bibleblock_quote.innerHTML=quote.quote):(console.info("Attempting to place in new modal"),(modalconfig={title:quote.heading,body:quote.quote},_modal.default.create?_modal.default.create(modalconfig):_modal_factory.default.create(modalconfig)).then((modal=>(modal.getRoot().on(_modal_events.default.hidden,(()=>{modal.destroy()})),modal.show(),modal))).catch(_notification.default.exception))})).catch((error=>{console.error("Error retrieving bible quote:",error),window.open(target.getAttribute("href"),"_bible_","width=500,height=800")})),event.preventDefault(),!1}Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.init=function(){if(!initialized){initialized=!0;const elements=document.querySelectorAll("a.bible-link[data-verseinfo]");console.info("Found elements",elements),elements.forEach((el=>{console.info("Handling element",el),el.addEventListener("click",bible_link)}))}},_modal=_interopRequireDefault(_modal),_modal_factory=_interopRequireDefault(_modal_factory),_modal_events=_interopRequireDefault(_modal_events),_notification=_interopRequireDefault(_notification);let initialized=!1}));
define("filter_bibleversesnwt/filter_bibleversesnwt",["exports","core/ajax","core/modal","core/modal_factory","core/modal_events","core/notification"],(function(_exports,_ajax,_modal,_modal_factory,_modal_events,_notification){function _interopRequireDefault(obj){return obj&&obj.__esModule?obj:{default:obj}}Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.init=function(){if(!initialized){initialized=!0;const elements=document.querySelectorAll("a.bible-link[data-verseinfo]");console.info("Found elements",elements),elements.forEach((el=>{console.info("Handling element",el),el.addEventListener("click",bible_link);getQuote(JSON.parse(el.getAttribute("data-verseinfo")))}))}},_modal=_interopRequireDefault(_modal),_modal_factory=_interopRequireDefault(_modal_factory),_modal_events=_interopRequireDefault(_modal_events),_notification=_interopRequireDefault(_notification);const Preloaded={};function getQuote(info){const key=`${info.lang}|${info.book}.${info.ch}:${info.verse}-${info.book_end}.${info.ch_end}:${info.verse_end}`;return new Promise(((resolve,reject)=>{key in Preloaded?resolve(Preloaded[key]):(0,_ajax.call)([{methodname:"filter_bibleversesnwt_get_biblequote",args:{lang:info.lang,book:info.book,ch:info.ch,verse:info.verse,book_end:info.book,ch_end:info.ch_end,verse_end:info.verse_end}}])[0].then((quote=>{Preloaded[key]=quote,resolve(quote)})).catch((error=>{reject(error)}))}))}function bible_link(event){const target=event.target,info=JSON.parse(target.getAttribute("data-verseinfo")),bibleblock_heading=document.querySelector("#block_bibleblock_heading"),bibleblock_quote=document.querySelector("#block_bibleblock_content");return bibleblock_quote&&(bibleblock_heading&&(bibleblock_heading.innerHTML=""),bibleblock_quote.innerHTML='<div class="spinner-border text-info"></div>'),getQuote(info).then((quote=>{var modalconfig;console.info("Got bible quote",quote),bibleblock_quote?(console.info("Attempting to place in verses block",bibleblock_heading,bibleblock_quote),bibleblock_heading&&(bibleblock_heading.innerHTML=quote.heading),bibleblock_quote.innerHTML=quote.quote):(console.info("Attempting to place in new modal"),(modalconfig={title:quote.heading,body:quote.quote},_modal.default.create?_modal.default.create(modalconfig):_modal_factory.default.create(modalconfig)).then((modal=>(modal.getRoot().on(_modal_events.default.hidden,(()=>{modal.destroy()})),modal.show(),modal))).catch(_notification.default.exception))})).catch((error=>{console.error("Error retrieving bible quote:",error),window.open(target.getAttribute("href"),"_bible_","width=500,height=800")})),event.preventDefault(),!1}let initialized=!1}));
//# sourceMappingURL=filter_bibleversesnwt.min.js.map

File diff suppressed because one or more lines are too long

View File

@ -24,43 +24,36 @@ function modalcreate(modalconfig) {
return ModalFactory.create(modalconfig);
}
}
const Preloaded = {};
/**
*
* @param {*} lang
* @param {*} book
* @param {*} ch
* @param {*} verse
* @param {*} book_end
* @param {*} ch_end
* @param {*} verse_end
* @param {*} info
*/
function getBibleQuote(lang,book,ch,verse,book_end, ch_end, verse_end) {
return new Promise((resolve, reject) => {
let range = "00000000";
let url = "";
range = book.toString() + ch.toString().padStart(3,'0') + verse.toString().padStart(3,'0');
if(book_end && ch_end && verse_end) {
range = range + "-" + book_end.toString() + ch_end.toString().padStart(3,'0') + verse_end.toString().padStart(3,'0');
function getQuote(info) {
const key = `${info.lang}|${info.book}.${info.ch}:${info.verse}-${info.book_end}.${info.ch_end}:${info.verse_end}`;
return new Promise((resolve,reject) => {
if (key in Preloaded) {
resolve(Preloaded[key]);
} else {
call([{
methodname: 'filter_bibleversesnwt_get_biblequote',
args: {
lang: info.lang,
book: info.book,
ch: info.ch,
verse: info.verse,
book_end: info.book,
ch_end: info.ch_end,
verse_end: info.verse_end}
}])[0].then((quote) => {
Preloaded[key] = quote;
resolve(quote);
}).catch((error) => {
reject(error);
});
}
if (lang == "nl") {
url = `https://www.jw.org/nl/bibliotheek/bijbel/nwt/boeken/json/html/${range}`;
} else { // if $lang == 'en'
url = `https://www.jw.org/en/library/bible/nwt/books/json/html/${range}`;
}
window.fetch(url).then((response) => {
try {
const o = JSON.parse();
resolve(o.ranges[range]);
} catch (error) {
reject("Error parsing json response",error, response);
}
}).catch((error) => {
reject("Error retrieving url",error);
});
});
}
@ -79,17 +72,8 @@ function bible_link(event) {
}
bibleblock_quote.innerHTML = `<div class="spinner-border text-info"></div>`;
}
call([{
methodname: 'filter_bibleversesnwt_get_biblequote',
args: {
lang: info.lang,
book: info.book,
ch: info.ch,
verse: info.verse,
book_end: info.book,
ch_end: info.ch,
verse_end: info.verse_end}
}])[0].then((quote) => {
getQuote(info).then((quote) => {
console.info("Got bible quote",quote);
if( bibleblock_quote ) {
console.info("Attempting to place in verses block",bibleblock_heading,bibleblock_quote);
@ -141,6 +125,8 @@ export function init() {
elements.forEach((el) => {
console.info("Handling element",el);
el.addEventListener("click", bible_link);
const info = JSON.parse(el.getAttribute("data-verseinfo"));
getQuote(info);
});
}
}

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -16,17 +16,17 @@ class bible {
return $languages;
}
private function wolhref($book,$chapter,$verse,$verse_end=0){
private function wolhref($book,$chapter,$verse,$chapter_end,$verse_end=0){
$book = ($book > 0)?$book:1;
$chapter = ($chapter >0)?$chapter:1;
$verse = ($verse > 0)?$verse:1;
$verse_end = ($verse_end > $verse)?$verse_end:$verse;
if($this->lang == "nl"){
return "https://wol.jw.org/nl/wol/b/r18/lp-o/nwtsty/{$book}/{$chapter}#v={$book}:{$chapter}:{$verse}-{$book}:{$chapter}:{$verse_end}";
return "https://wol.jw.org/nl/wol/b/r18/lp-o/nwtsty/{$book}/{$chapter}#v={$book}:{$chapter}:{$verse}-{$book}:{$chapter_end}:{$verse_end}";
}
else { // if $this->lang == 'en'
return "https://wol.jw.org/nl/wol/b/r1/lp-e/nwtsty/{$book}/{$chapter}#v={$book}:{$chapter}:{$verse}-{$book}:{$chapter}:{$verse_end}";
return "https://wol.jw.org/nl/wol/b/r1/lp-e/nwtsty/{$book}/{$chapter}#v={$book}:{$chapter}:{$verse}-{$book}:{$chapter_end}:{$verse_end}";
}
}
@ -185,21 +185,24 @@ class bible {
$names = $this->books[$booknum];
foreach($names as $bookname){
$re = "/([1-3]?\s?\b{$bookname})\s*?(\d*):(\d+)(?:\s*?[-,]\s*?(\d+))?/i";
$re = "/(\b{$bookname})\h*?(\d*):(\d+)(?:\h*[-,]\h*(\d+)(?::(\d+))?)?/i";
// First check the presence of the bookname before
if( ($ix = stripos($content,$bookname)) !== false){
$matches = [];
if ( ($ix = stripos($content,$bookname)) !== false ) {
$lang = $this->lang;
$content = preg_replace_callback($re,function ($m) use ($lang,$booknum, $bookname){
$book = strtolower(trim($m[1]));
$ch = $m[2];
$verse = $m[3];
$verse_to = (count($m)>4)?$m[4]:0;
$ch_end = (count($m)>5)?$m[4]:$ch;
$verse_to = (count($m)>5)?$m[5]:((count($m)>4)?$m[4]:0);
if($book == $bookname){ // Check if name matches
$href = $this->wolhref($lang, $booknum, $ch, $verse, $verse_to);
$versedata = json_encode(["lang" => $lang, "book" => $booknum, "ch" => $ch, "verse" => $verse, "verse_end" => $verse_to, "wolhref" => $href]);
$href = $this->wolhref($booknum, $ch, $verse, $ch_end, $verse_to);
$versedata = json_encode([ "lang" => $lang, "book" => $booknum,
"ch" => $ch, "verse" => $verse,
"ch_end" => $ch_end, "verse_end" => $verse_to,
"wolhref" => $href]);
return "<a href='{$href}' data-verseinfo='{$versedata}' target='_bible_' class='bible-link'>".$m[0]."</a>";
} else {
return $m[0];

View File

@ -63,33 +63,72 @@ class bibleservice extends \external_api {
* @return array
*/
public static function get_biblequote($lang,$book,$ch,$verse,$book_end = null,$ch_end = null,$verse_end = null) {
$range = $book .str_pad($ch,3,'0',STR_PAD_LEFT) . str_pad($verse,3,'0',STR_PAD_LEFT);
global $DB;
$TABLE = "filter_bibleversesnwt";
if(!empty($book_end) && !empty($ch_end) && !empty($verse_end)) {
$range .= "-" . $book_end .str_pad($ch_end,3,'0',STR_PAD_LEFT) . str_pad($verse_end,3,'0',STR_PAD_LEFT);
}
$search = [
"lang" => $lang,
"book" => $book,
"ch"=> $ch,
"verse" => $verse,
"book_end" => $book_end,
"ch_end" => $ch_end,
"verse_end" => $verse_end,
];
if ($lang == "nl") {
$url = "https://www.jw.org/nl/bibliotheek/bijbel/nwt/boeken/json/html/{$range}";
} else { // if $lang == 'en'
$url = "https://www.jw.org/en/library/bible/nwt/books/json/html/{$range}";
}
$cache = $DB->get_record($TABLE,$search);
$now = time();
$ch = curl_init();
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_SSH_COMPRESSION, true);
$result = curl_exec($ch);
$o = json_decode($result,true);
if(isset($o["ranges"]) && isset($o["ranges"][$range])) {
$r = $o["ranges"][$range];
return [
"heading" => $r["citation"],
"quote" => preg_replace('#<a.*?>(.*?)</a>#i', '\1', $r["html"]),
];
if($cache && ($now - $cache->time_retrieved) < (24*3600)) {
// Return from cache.
$quote = json_decode($cache->content,true);
return $quote;
} else {
throw new \moodle_exception("Unexpected JSON code",'','',null,$result);
$range = $book .str_pad($ch,3,'0',STR_PAD_LEFT) . str_pad($verse,3,'0',STR_PAD_LEFT);
if(!empty($book_end) && !empty($ch_end) && !empty($verse_end)) {
$range .= "-" . $book_end .str_pad($ch_end,3,'0',STR_PAD_LEFT) . str_pad($verse_end,3,'0',STR_PAD_LEFT);
}
if ($lang == "nl") {
$url = "https://www.jw.org/nl/bibliotheek/bijbel/nwt/boeken/json/html/{$range}";
} else { // if $lang == 'en'
$url = "https://www.jw.org/en/library/bible/nwt/books/json/html/{$range}";
}
$ch = curl_init();
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_SSH_COMPRESSION, true);
$result = curl_exec($ch);
$o = json_decode($result,true);
if(isset($o["ranges"]) && isset($o["ranges"][$range])) {
$r = $o["ranges"][$range];
$quote = [
"heading" => $r["citation"],
"quote" => preg_replace('#<a.*?>(.*?)</a>#i', '\1', $r["html"]),
];
// Store bible verse into cache.
$quotejson = json_encode($quote);
if($cache) {
$cache->time_retrieved = time();
$cache->content = $quotejson;
$DB->update_record($TABLE,$cache);
} else {
$cache = (object)$search;
$cache->time_retrieved = time();
$cache->content = $quotejson;
$DB->insert_record($TABLE,$cache);
}
return $quote;
} else {
throw new \moodle_exception("Unexpected JSON code",'','',null,$result);
}
}
}

25
db/install.xml Normal file
View File

@ -0,0 +1,25 @@
<?xml version="1.0" encoding="UTF-8" ?>
<XMLDB PATH="filter/bibleversesnwt/db" VERSION="20240308" COMMENT="XMLDB file for Moodle filter/bibleversesnwt"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="../../../lib/xmldb/xmldb.xsd"
>
<TABLES>
<TABLE NAME="filter_bibleversesnwt" COMMENT="Default comment for filter_bibleversesnwt, please edit me">
<FIELDS>
<FIELD NAME="id" TYPE="int" LENGTH="10" NOTNULL="true" SEQUENCE="true"/>
<FIELD NAME="book" TYPE="int" LENGTH="5" NOTNULL="false" SEQUENCE="false"/>
<FIELD NAME="ch" TYPE="int" LENGTH="5" NOTNULL="false" SEQUENCE="false"/>
<FIELD NAME="verse" TYPE="int" LENGTH="5" NOTNULL="false" SEQUENCE="false"/>
<FIELD NAME="book_end" TYPE="int" LENGTH="5" NOTNULL="false" SEQUENCE="false"/>
<FIELD NAME="ch_end" TYPE="int" LENGTH="5" NOTNULL="false" SEQUENCE="false"/>
<FIELD NAME="verse_end" TYPE="int" LENGTH="5" NOTNULL="false" SEQUENCE="false"/>
<FIELD NAME="content" TYPE="text" NOTNULL="false" SEQUENCE="false"/>
<FIELD NAME="time_retrieved" TYPE="int" LENGTH="20" NOTNULL="false" SEQUENCE="false"/>
<FIELD NAME="lang" TYPE="char" LENGTH="12" NOTNULL="false" SEQUENCE="false"/>
</FIELDS>
<KEYS>
<KEY NAME="primary" TYPE="primary" FIELDS="id"/>
</KEYS>
</TABLE>
</TABLES>
</XMLDB>

92
db/upgrade.php Normal file
View File

@ -0,0 +1,92 @@
<?php
// This file is part of the Studyplan plugin for Moodle
//
// Moodle 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.
//
// Moodle 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 Moodle. If not, see <https://www.gnu.org/licenses/>.
/**
* Database upgrade script
* @package filter_bibleversesnwt
* @copyright 2023 P.M. Kuipers
* @license https://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
*/
/**
* Hook to upgrade database upon plugin upgrade
* @param mixed $oldversion Version of plugin database before upgrade
* @return bool Upgrade success status
*
*/
function xmldb_filter_bibleversesnwt_upgrade($oldversion) {
global $DB;
$dbman = $DB->get_manager();
if ($oldversion < 2024030800) {
// Define table filter_bibleversesnwt to be created.
$table = new xmldb_table('filter_bibleversesnwt');
// Adding fields to table filter_bibleversesnwt.
$table->add_field('id', XMLDB_TYPE_INTEGER, '10', null, XMLDB_NOTNULL, XMLDB_SEQUENCE, null);
$table->add_field('book', XMLDB_TYPE_INTEGER, '5', null, null, null, null);
$table->add_field('ch', XMLDB_TYPE_INTEGER, '5', null, null, null, null);
$table->add_field('verse', XMLDB_TYPE_INTEGER, '5', null, null, null, null);
$table->add_field('book_end', XMLDB_TYPE_INTEGER, '5', null, null, null, null);
$table->add_field('ch_end', XMLDB_TYPE_INTEGER, '5', null, null, null, null);
$table->add_field('verse_end', XMLDB_TYPE_INTEGER, '5', null, null, null, null);
$table->add_field('content', XMLDB_TYPE_TEXT, null, null, null, null, null);
// Adding keys to table filter_bibleversesnwt.
$table->add_key('primary', XMLDB_KEY_PRIMARY, ['id']);
// Conditionally launch create table for filter_bibleversesnwt.
if (!$dbman->table_exists($table)) {
$dbman->create_table($table);
}
// Bibleversesnwt savepoint reached.
upgrade_plugin_savepoint(true, 2024030800, 'filter', 'bibleversesnwt');
}
if ($oldversion < 2024030801) {
// Define field time_retrieved to be added to filter_bibleversesnwt.
$table = new xmldb_table('filter_bibleversesnwt');
$field = new xmldb_field('time_retrieved', XMLDB_TYPE_INTEGER, '20', null, null, null, null, 'content');
// Conditionally launch add field time_retrieved.
if (!$dbman->field_exists($table, $field)) {
$dbman->add_field($table, $field);
}
// Bibleversesnwt savepoint reached.
upgrade_plugin_savepoint(true, 2024030801, 'filter', 'bibleversesnwt');
}
if ($oldversion < 2024030802) {
// Define field lang to be added to filter_bibleversesnwt.
$table = new xmldb_table('filter_bibleversesnwt');
$field = new xmldb_field('lang', XMLDB_TYPE_CHAR, '12', null, null, null, null, 'time_retrieved');
// Conditionally launch add field lang.
if (!$dbman->field_exists($table, $field)) {
$dbman->add_field($table, $field);
}
// Bibleversesnwt savepoint reached.
upgrade_plugin_savepoint(true, 2024030802, 'filter', 'bibleversesnwt');
}
return true;
}

View File

@ -24,7 +24,7 @@
defined('MOODLE_INTERNAL') || die();
$plugin->version = 2023112000;
$plugin->version = 2024030802;
$plugin->requires = 2021051700; // YYYYMMDDHH (This is the release version for Moodle 3.11)
$plugin->component = 'filter_bibleversesnwt';
$plugin->maturity = MATURITY_STABLE;