Use the user data reference to access corpora, jobs or query results. Now all values should update as they should in lists an displays

This commit is contained in:
Patrick Jentsch 2021-02-01 09:57:10 +01:00
parent 54be3b4a79
commit 37f98bb4ec
9 changed files with 63 additions and 74 deletions

View File

@ -1,20 +1,19 @@
class CorpusDisplay extends RessourceDisplay { class CorpusDisplay extends RessourceDisplay {
constructor(displayElement) { constructor(displayElement) {
super(displayElement); super(displayElement);
this.corpus = undefined; this.corpusId = displayElement.dataset.corpusId;
this.user.eventListeners.corpus.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), displayElement.dataset.corpusId); this.user.eventListeners.corpus.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), this.corpusId);
} }
init(corpus) { init() {
this.corpus = corpus;
for (let exportCorpusTriggerElement of this.displayElement.querySelectorAll('.export-corpus-trigger')) {exportCorpusTriggerElement.addEventListener('click', () => this.requestCorpusExport());} for (let exportCorpusTriggerElement of this.displayElement.querySelectorAll('.export-corpus-trigger')) {exportCorpusTriggerElement.addEventListener('click', () => this.requestCorpusExport());}
nopaque.appClient.socket.on(`export_corpus_${this.corpus.id}`, () => this.downloadCorpus()); nopaque.appClient.socket.on(`export_corpus_${this.user.data.corpora[this.corpusId].id}`, () => this.downloadCorpus());
this.setCreationDate(this.corpus.creation_date); this.setCreationDate(this.user.data.corpora[this.corpusId].creation_date);
this.setDescription(this.corpus.description); this.setDescription(this.user.data.corpora[this.corpusId].description);
this.setLastEditedDate(this.corpus.last_edited_date); this.setLastEditedDate(this.user.data.corpora[this.corpusId].last_edited_date);
this.setStatus(this.corpus.status); this.setStatus(this.user.data.corpora[this.corpusId].status);
this.setTitle(this.corpus.title); this.setTitle(this.user.data.corpora[this.corpusId].title);
this.setTokenRatio(this.corpus.current_nr_of_tokens, this.corpus.max_nr_of_tokens); this.setTokenRatio(this.user.data.corpora[this.corpusId].current_nr_of_tokens, this.user.data.corpora[this.corpusId].max_nr_of_tokens);
} }
patch(patch) { patch(patch) {
@ -23,10 +22,10 @@ class CorpusDisplay extends RessourceDisplay {
switch(operation.op) { switch(operation.op) {
case 'replace': case 'replace':
// Matches: /jobs/{this.job.id}/status // Matches: /jobs/{this.job.id}/status
re = new RegExp('^/corpora/' + this.corpus.id + '/last_edited_date'); re = new RegExp('^/corpora/' + this.user.data.corpora[this.corpusId].id + '/last_edited_date');
if (re.test(operation.path)) {this.setLastEditedDate(operation.value); break;} if (re.test(operation.path)) {this.setLastEditedDate(operation.value); break;}
// Matches: /jobs/{this.job.id}/status // Matches: /jobs/{this.job.id}/status
re = new RegExp('^/corpora/' + this.corpus.id + '/status$'); re = new RegExp('^/corpora/' + this.user.data.corpora[this.corpusId].id + '/status$');
if (re.test(operation.path)) {this.setStatus(operation.value); break;} if (re.test(operation.path)) {this.setStatus(operation.value); break;}
break; break;
default: default:
@ -36,7 +35,7 @@ class CorpusDisplay extends RessourceDisplay {
} }
requestCorpusExport() { requestCorpusExport() {
nopaque.appClient.socket.emit('export_corpus', this.corpus.id); nopaque.appClient.socket.emit('export_corpus', this.user.data.corpora[this.corpusId].id);
nopaque.flash('Preparing your corpus export...', 'corpus'); nopaque.flash('Preparing your corpus export...', 'corpus');
for (let exportCorpusTriggerElement of this.displayElement.querySelectorAll('.export-corpus-trigger')) {exportCorpusTriggerElement.classList.toggle('disabled', true);} for (let exportCorpusTriggerElement of this.displayElement.querySelectorAll('.export-corpus-trigger')) {exportCorpusTriggerElement.classList.toggle('disabled', true);}
} }
@ -46,7 +45,7 @@ class CorpusDisplay extends RessourceDisplay {
for (let exportCorpusTriggerElement of this.displayElement.querySelectorAll('.export-corpus-trigger')) {exportCorpusTriggerElement.classList.toggle('disabled', false);} for (let exportCorpusTriggerElement of this.displayElement.querySelectorAll('.export-corpus-trigger')) {exportCorpusTriggerElement.classList.toggle('disabled', false);}
// Little trick to call the download view after ziping has finished // Little trick to call the download view after ziping has finished
let fakeBtn = document.createElement('a'); let fakeBtn = document.createElement('a');
fakeBtn.href = `/corpora/${this.corpus.id}/download`; fakeBtn.href = `/corpora/${this.user.data.corpora[this.corpusId].id}/download`;
fakeBtn.click(); fakeBtn.click();
} }
@ -72,7 +71,7 @@ class CorpusDisplay extends RessourceDisplay {
} }
} }
for (let element of this.displayElement.querySelectorAll('.build-corpus-trigger')) { for (let element of this.displayElement.querySelectorAll('.build-corpus-trigger')) {
if (status === 'unprepared' && Object.values(this.corpus.files).length > 0) { if (status === 'unprepared' && Object.values(this.user.data.corpora[this.corpusId].files).length > 0) {
element.classList.remove('disabled'); element.classList.remove('disabled');
} else { } else {
element.classList.add('disabled'); element.classList.add('disabled');

View File

@ -1,20 +1,19 @@
class JobDisplay extends RessourceDisplay { class JobDisplay extends RessourceDisplay {
constructor(displayElement) { constructor(displayElement) {
super(displayElement); super(displayElement);
this.job = undefined; this.jobId = displayElement.dataset.jobId;
this.user.eventListeners.job.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), displayElement.dataset.jobId); this.user.eventListeners.job.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), this.jobId);
} }
init(job) { init(job) {
this.job = job; this.setCreationDate(this.user.data.jobs[this.jobId].creation_date);
this.setCreationDate(this.job.creation_date); this.setEndDate(this.user.data.jobs[this.jobId].creation_date);
this.setEndDate(this.job.creation_date); this.setDescription(this.user.data.jobs[this.jobId].description);
this.setDescription(this.job.description); this.setService(this.user.data.jobs[this.jobId].service);
this.setService(this.job.service); this.setServiceArgs(this.user.data.jobs[this.jobId].service_args);
this.setServiceArgs(this.job.service_args); this.setServiceVersion(this.user.data.jobs[this.jobId].service_version);
this.setServiceVersion(this.job.service_version); this.setStatus(this.user.data.jobs[this.jobId].status);
this.setStatus(this.job.status); this.setTitle(this.user.data.jobs[this.jobId].title);
this.setTitle(this.job.title);
} }
patch(patch) { patch(patch) {
@ -22,11 +21,11 @@ class JobDisplay extends RessourceDisplay {
for (let operation of patch) { for (let operation of patch) {
switch(operation.op) { switch(operation.op) {
case 'replace': case 'replace':
// Matches: /jobs/{this.job.id}/status // Matches: /jobs/{this.user.data.jobs[this.jobId].id}/status
re = new RegExp('^/jobs/' + this.job.id + '/end_date'); re = new RegExp('^/jobs/' + this.user.data.jobs[this.jobId].id + '/end_date');
if (re.test(operation.path)) {this.setEndDate(operation.value); break;} if (re.test(operation.path)) {this.setEndDate(operation.value); break;}
// Matches: /jobs/{this.job.id}/status // Matches: /jobs/{this.user.data.jobs[this.jobId].id}/status
re = new RegExp('^/jobs/' + this.job.id + '/status$'); re = new RegExp('^/jobs/' + this.user.data.jobs[this.jobId].id + '/status$');
if (re.test(operation.path)) {this.setStatus(operation.value); break;} if (re.test(operation.path)) {this.setStatus(operation.value); break;}
break; break;
default: default:

View File

@ -1,13 +1,12 @@
class CorpusFileList extends RessourceList { class CorpusFileList extends RessourceList {
constructor(listElement, options = {}) { constructor(listElement, options = {}) {
super(listElement, {...CorpusFileList.options, ...options}); super(listElement, {...CorpusFileList.options, ...options});
this.corpus = undefined; this.corpusId = listElement.dataset.corpusId;
this.user.eventListeners.corpus.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), listElement.dataset.corpusId); this.user.eventListeners.corpus.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), this.corpusId);
} }
init(corpus) { init() {
this.corpus = corpus; super.init(this.user.data.corpora[this.corpusId].files);
super.init(this.corpus.files);
} }
onclick(event) { onclick(event) {
@ -22,11 +21,11 @@ class CorpusFileList extends RessourceList {
let deleteModalHTML = `<div class="modal"> let deleteModalHTML = `<div class="modal">
<div class="modal-content"> <div class="modal-content">
<h4>Confirm corpus deletion</h4> <h4>Confirm corpus deletion</h4>
<p>Do you really want to delete the corpus file <b>${this.corpus.files[corpusFileId].filename}</b>? It will be permanently deleted!</p> <p>Do you really want to delete the corpus file <b>${this.user.data.corpora[this.corpusId].files[corpusFileId].filename}</b>? It will be permanently deleted!</p>
</div> </div>
<div class="modal-footer"> <div class="modal-footer">
<a href="#!" class="btn modal-close waves-effect waves-light">Cancel</a> <a href="#!" class="btn modal-close waves-effect waves-light">Cancel</a>
<a class="btn modal-close red waves-effect waves-light" href="${this.corpus.files[corpusFileId].url}/delete"><i class="material-icons left">delete</i>Delete</a> <a class="btn modal-close red waves-effect waves-light" href="${this.user.data.corpora[this.corpusId].files[corpusFileId].url}/delete"><i class="material-icons left">delete</i>Delete</a>
</div> </div>
</div>`; </div>`;
let deleteModalParentElement = document.querySelector('main'); let deleteModalParentElement = document.querySelector('main');
@ -36,10 +35,10 @@ class CorpusFileList extends RessourceList {
deleteModal.open(); deleteModal.open();
break; break;
case 'download': case 'download':
window.location.href = this.corpus.files[corpusFileId].download_url; window.location.href = this.user.data.corpora[this.corpusId].files[corpusFileId].download_url;
break; break;
case 'view': case 'view':
if (corpusFileId !== '-1') {window.location.href = this.corpus.files[corpusFileId].url;} if (corpusFileId !== '-1') {window.location.href = this.user.data.corpora[this.corpusId].files[corpusFileId].url;}
break; break;
default: default:
console.error(`Unknown action: "${action}"`); console.error(`Unknown action: "${action}"`);
@ -52,13 +51,13 @@ class CorpusFileList extends RessourceList {
for (let operation of patch) { for (let operation of patch) {
switch(operation.op) { switch(operation.op) {
case 'add': case 'add':
// Matches the only paths that should be handled here: /corpora/{this.corpus.id}/files/{corpusFileId} // Matches the only paths that should be handled here: /corpora/{this.user.data.corpora[this.corpusId].id}/files/{corpusFileId}
re = new RegExp('^/corpora/' + this.corpus.id + '/files/(\\d+)$'); re = new RegExp('^/corpora/' + this.user.data.corpora[this.corpusId].id + '/files/(\\d+)$');
if (re.test(operation.path)) {this.add(operation.value);} if (re.test(operation.path)) {this.add(operation.value);}
break; break;
case 'remove': case 'remove':
// See case add ;) // See case add ;)
re = new RegExp('^/corpora/' + this.corpus.id + '/files/(\\d+)$'); re = new RegExp('^/corpora/' + this.user.data.corpora[this.corpusId].id + '/files/(\\d+)$');
if (re.test(operation.path)) { if (re.test(operation.path)) {
[match, id] = operation.path.match(re); [match, id] = operation.path.match(re);
this.remove(id); this.remove(id);
@ -66,7 +65,7 @@ class CorpusFileList extends RessourceList {
break; break;
case 'replace': case 'replace':
// Matches the only paths that should be handled here: /corpora/{corpusId}/{status || description || title} // Matches the only paths that should be handled here: /corpora/{corpusId}/{status || description || title}
re = new RegExp('^/corpora/' + this.corpus.id + '/files/(\\d+)/(author|filename|publishing_year|title)$'); re = new RegExp('^/corpora/' + this.user.data.corpora[this.corpusId].id + '/files/(\\d+)/(author|filename|publishing_year|title)$');
if (re.test(operation.path)) { if (re.test(operation.path)) {
[match, id, valueName] = operation.path.match(re); [match, id, valueName] = operation.path.match(re);
this.replace(id, valueName, operation.value); this.replace(id, valueName, operation.value);

View File

@ -1,13 +1,11 @@
class CorpusList extends RessourceList { class CorpusList extends RessourceList {
constructor(listElement, options = {}) { constructor(listElement, options = {}) {
super(listElement, {...CorpusList.options, ...options}); super(listElement, {...CorpusList.options, ...options});
this.corpora = undefined;
this.user.eventListeners.corpus.addEventListener((eventType, payload) => this.eventHandler(eventType, payload)); this.user.eventListeners.corpus.addEventListener((eventType, payload) => this.eventHandler(eventType, payload));
} }
init(corpora) { init() {
this.corpora = corpora; super.init(this.user.data.corpora);
super.init(corpora);
} }
onclick(event) { onclick(event) {
@ -21,11 +19,11 @@ class CorpusList extends RessourceList {
let deleteModalHTML = `<div class="modal"> let deleteModalHTML = `<div class="modal">
<div class="modal-content"> <div class="modal-content">
<h4>Confirm corpus deletion</h4> <h4>Confirm corpus deletion</h4>
<p>Do you really want to delete the corpus <b>${this.corpora[corpusId].title}</b>? All files will be permanently deleted!</p> <p>Do you really want to delete the corpus <b>${this.user.data.corpora[corpusId].title}</b>? All files will be permanently deleted!</p>
</div> </div>
<div class="modal-footer"> <div class="modal-footer">
<a href="#!" class="btn modal-close waves-effect waves-light">Cancel</a> <a href="#!" class="btn modal-close waves-effect waves-light">Cancel</a>
<a class="btn modal-close red waves-effect waves-light" href="${this.corpora[corpusId].url}/delete"><i class="material-icons left">delete</i>Delete</a> <a class="btn modal-close red waves-effect waves-light" href="${this.user.data.corpora[corpusId].url}/delete"><i class="material-icons left">delete</i>Delete</a>
</div> </div>
</div>`; </div>`;
let deleteModalParentElement = document.querySelector('main'); let deleteModalParentElement = document.querySelector('main');
@ -35,7 +33,7 @@ class CorpusList extends RessourceList {
deleteModal.open(); deleteModal.open();
break; break;
case 'view': case 'view':
if (corpusId !== '-1') {window.location.href = this.corpora[corpusId].url;} if (corpusId !== '-1') {window.location.href = this.user.data.corpora[corpusId].url;}
break; break;
default: default:
console.error(`Unknown action: ${action}`); console.error(`Unknown action: ${action}`);

View File

@ -1,13 +1,12 @@
class JobInputList extends RessourceList { class JobInputList extends RessourceList {
constructor(listElement, options = {}) { constructor(listElement, options = {}) {
super(listElement, {...JobInputList.options, ...options}); super(listElement, {...JobInputList.options, ...options});
this.job = undefined; this.jobId = listElement.dataset.jobId;
this.user.eventListeners.job.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), listElement.dataset.jobId); this.user.eventListeners.job.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), this.jobId);
} }
init(job) { init() {
this.job = job; super.init(this.user.data.jobs[this.jobId].inputs);
super.init(this.job.inputs);
} }
onclick(event) { onclick(event) {
@ -19,7 +18,7 @@ class JobInputList extends RessourceList {
let action = actionButtonElement.dataset.action; let action = actionButtonElement.dataset.action;
switch (action) { switch (action) {
case 'download': case 'download':
window.location.href = this.job.inputs[jobInputId].download_url; window.location.href = this.user.data.jobs[this.jobId].inputs[jobInputId].download_url;
break; break;
default: default:
console.error(`Unknown action: "${action}"`); console.error(`Unknown action: "${action}"`);

View File

@ -1,13 +1,11 @@
class JobList extends RessourceList { class JobList extends RessourceList {
constructor(listElement, options = {}) { constructor(listElement, options = {}) {
super(listElement, {...JobList.options, ...options}); super(listElement, {...JobList.options, ...options});
this.jobs = undefined;
this.user.eventListeners.job.addEventListener((eventType, payload) => this.eventHandler(eventType, payload)); this.user.eventListeners.job.addEventListener((eventType, payload) => this.eventHandler(eventType, payload));
} }
init(jobs) { init() {
this.jobs = jobs; super.init(this.user.data.jobs);
super.init(jobs);
} }
onclick(event) { onclick(event) {

View File

@ -1,13 +1,12 @@
class JobResultList extends RessourceList { class JobResultList extends RessourceList {
constructor(listElement, options = {}) { constructor(listElement, options = {}) {
super(listElement, {...JobResultList.options, ...options}); super(listElement, {...JobResultList.options, ...options});
this.job = undefined; this.jobId = listElement.dataset.jobId;
this.user.eventListeners.job.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), listElement.dataset.jobId); this.user.eventListeners.job.addEventListener((eventType, payload) => this.eventHandler(eventType, payload), this.jobId);
} }
init(job) { init() {
this.job = job; super.init(this.user.data.jobs[this.jobId].results);
super.init(this.job.results);
} }
onclick(event) { onclick(event) {
@ -19,7 +18,7 @@ class JobResultList extends RessourceList {
let action = actionButtonElement.dataset.action; let action = actionButtonElement.dataset.action;
switch (action) { switch (action) {
case 'download': case 'download':
window.location.href = this.job.results[jobResultId].download_url; window.location.href = this.user.data.jobs[this.jobId].results[jobResultId].download_url;
break; break;
default: default:
console.error(`Unknown action: "${action}"`); console.error(`Unknown action: "${action}"`);
@ -32,8 +31,8 @@ class JobResultList extends RessourceList {
for (let operation of patch) { for (let operation of patch) {
switch(operation.op) { switch(operation.op) {
case 'add': case 'add':
// Matches the only paths that should be handled here: /jobs/{this.job.id}/results/{jobResultId} // Matches the only paths that should be handled here: /jobs/{this.user.data.jobs[this.jobId].id}/results/{jobResultId}
re = new RegExp('^/jobs/' + this.job.id + '/results/(\\d+)$'); re = new RegExp('^/jobs/' + this.user.data.jobs[this.jobId].id + '/results/(\\d+)$');
if (re.test(operation.path)) {this.add(operation.value);} if (re.test(operation.path)) {this.add(operation.value);}
break; break;
default: default:

View File

@ -1,13 +1,11 @@
class QueryResultList extends RessourceList { class QueryResultList extends RessourceList {
constructor(listElement, options = {}) { constructor(listElement, options = {}) {
super(listElement, {...QueryResultList.options, ...options}); super(listElement, {...QueryResultList.options, ...options});
this.queryResults = undefined;
this.user.eventListeners.queryResult.addEventListener((eventType, payload) => this.eventHandler(eventType, payload)); this.user.eventListeners.queryResult.addEventListener((eventType, payload) => this.eventHandler(eventType, payload));
} }
init(queryResults) { init() {
this.queryResults = queryResults; super.init(this.user.data.query_results);
super.init(queryResults);
} }
onclick(event) { onclick(event) {

View File

@ -45,7 +45,7 @@ class RessourceList {
eventHandler(eventType, payload) { eventHandler(eventType, payload) {
switch (eventType) { switch (eventType) {
case 'init': case 'init':
this.init(payload); this.init();
break; break;
case 'patch': case 'patch':
this.patch(payload); this.patch(payload);