Skip to content

Commit

Permalink
Simplify datatables calls, rendering.
Browse files Browse the repository at this point in the history
  • Loading branch information
jzohrab committed Sep 22, 2024
1 parent 3115f8f commit 74342c5
Show file tree
Hide file tree
Showing 12 changed files with 145 additions and 153 deletions.
1 change: 0 additions & 1 deletion lute/book/datatables.py
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,6 @@ def get_data_tables_list(parameters, is_archived):
if language_id != 0:
base_sql += f" and LgID = {language_id}"

# print(base_sql)
session = db.session
connection = session.connection()

Expand Down
4 changes: 4 additions & 0 deletions lute/book/routes.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,10 @@ def _load_term_custom_filters(request_form, parameters):

def datatables_source(is_archived):
"Get datatables json for books."
# In the future, we might want to create an API such as
# get_books(sort_order, search_string, length, index, language_id).
# See DataTablesFlaskParamParser.parse_params_2(request.form)
# (currently unused)
parameters = DataTablesFlaskParamParser.parse_params(request.form)
_load_term_custom_filters(request.form, parameters)
data = get_data_tables_list(parameters, is_archived)
Expand Down
2 changes: 1 addition & 1 deletion lute/bookmarks/datatables.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ def get_data_tables_list(parameters, book_id):
"Bookmark json data for datatables."

base_sql = f"""
SELECT tb.TbID, tb.TbTxID, tb.TbTitle, tx.TxText, tx.TxOrder
SELECT tb.TbID, tb.TbTxID, tb.TbTitle, tx.TxOrder
FROM textbookmarks as tb
INNER JOIN texts as tx ON tb.TbTxID = tx.TxID
WHERE tx.TxBkID = { book_id }
Expand Down
50 changes: 20 additions & 30 deletions lute/templates/book/tablelisting.html
Original file line number Diff line number Diff line change
Expand Up @@ -68,8 +68,7 @@
},
buttons: [
{
extend: 'colvis',
columns: '.colVisToggled'
extend: 'colvis'
}
],
{% if status != 'Archived' %}
Expand All @@ -89,24 +88,15 @@
stateSave: true,
stateDuration: 0, /* never expire saved state. */
search: { search: initial_search },
columnDefs: [
{ "name": "BkTitle", "targets": 0, "width": "40%", "render": render_book_title, className: "colVisToggled" },
{ "name": "LgName", "targets": 1, "width": "10%", className: "colVisToggled" },
{ "name": "TagList", "targets": 2, "width": "10%", className: "colVisToggled" },
{ "name": "WordCount", "targets": 3, "width": "10%", className: "colVisToggled" },
{ "name": "UnknownPercent", "targets": 4, "data": null, "searchable": true, "orderable": true, "render": render_book_stats_graph, className: "colVisToggled" },
{ "targets": 5, "data": null, "width": "8%", "searchable": false, "orderable": false, "render": render_book_actions, className: "colVisToggled" },

/* Extra data that is returned in the row for rendering, but not shown, not changed by colvis. */
{ "name": "BkID", "targets": 6, "data": null, "visible": false },
{ "name": "BkArchived", "targets": 7, "data": null, "visible": false },
{ "name": "PageCount", "targets": 8, "data": null, "visible": false },
{ "name": "PageNum", "targets": 9, "data": null, "visible": false },
{ "name": "IsCompleted", "targets": 10, "data": null, "visible": false },
{ "name": "StatusDistribution", "targets": 11, "data": null, "visible": false },
columns: [
{ name: "BkTitle", width: "40%", render: render_book_title },
{ name: "LgName", width: "10%", data: "LgName" },
{ name: "TagList", width: "10%", data: "TagList" },
{ name: "WordCount", width: "10%", data: "WordCount" },
{ name: "UnknownPercent", render: render_book_stats_graph },
{ width: "8%", "searchable": false, "orderable": false, render: render_book_actions },
],

// Ajax call
ajax: {
url: "/book/datatables/{{ status or 'active' }}",
// Additional filters. func calls are required to get the
Expand All @@ -121,9 +111,6 @@
},

});

// var dropdown = $('#defaultLanguageSelect');
// $('div.toolbar').append(dropdown);
} // end setup_book_datatable


Expand Down Expand Up @@ -209,13 +196,16 @@
do_action_post('delete', bookid);
}

// Rendering helpers. =================================================
// each row in the table is a json dict, the keys are the SQL column names.

let render_book_title = function ( data, type, row, meta ) {
const bkid = parseInt(row[5]);
const pgnum = parseInt(row[8]);
const pgcount = parseInt(row[7]);
const bkid = parseInt(row['BkID']);
const pgnum = parseInt(row['PageNum']);
const pgcount = parseInt(row['PageCount']);
let pgfraction = '';

const completed = (parseInt(row[9]) == 1);
const completed = (parseInt(row['IsCompleted']) == 1);
let book_title_classes = ['book-title'];
if (completed) {
book_title_classes.push('completed_book');
Expand All @@ -224,13 +214,13 @@
pgfraction = ` (${pgnum}/${pgcount})`;
}

return `<a class="${book_title_classes.join(' ')}" href="/read/${bkid}">${row[0]}${pgfraction}</a>`;
return `<a class="${book_title_classes.join(' ')}" href="/read/${bkid}">${row['BkTitle']}${pgfraction}</a>`;
};


let render_book_stats_graph = function(data, type, row, meta) {
const empty_stats = `<div title="Please open the book to calculate stats">&nbsp;</div>`;
let statuscounts = row[10];
let statuscounts = row['StatusDistribution'];
if ((statuscounts ?? '')== '') {
return empty_stats;
}
Expand Down Expand Up @@ -285,9 +275,9 @@

let render_book_actions = function ( data, type, row, meta ) {
// TODO zzfuture fix: security - add CSRF token
const bkid = row[5];
const bktitle = encodeURIComponent(row[0]);
const is_active = (row[6] == 0);
const bkid = row['BkID'];
const bktitle = encodeURIComponent(row['BkTitle']);
const is_active = (row['BkArchived'] == 0);

const links = [];
const make_link = function(label, func) {
Expand Down
22 changes: 8 additions & 14 deletions lute/templates/bookmarks/list.html
Original file line number Diff line number Diff line change
Expand Up @@ -55,18 +55,14 @@ <h1>{{ book.title }}</h1>
],
bottomEnd: 'paging'
},
columnDefs: [
{ "name": "TxOrder", "targets": 0, "width": "5%", className: "colVisToggled" },
{ "name": "TbTitle", "targets": 1, "width": "70%", className: "colVisToggled", "render": render_page_link },
{ "targets": 2, "data": null, "width": "15%", "searchable": false, "orderable": false, "render": render_bookmark_actions, className: "colVisToggled" },

// Hidden data for processing bookmark actions
{ "name": "TbID", "targets": 3, "data": null, "visible": false },
columns: [
{ name: "TxOrder", data: "TxOrder", width: "5%" },
{ name: "TbTitle", width: "70%", render: render_page_link },
{ data: null, width: "15%", searchable: false, orderable: false, render: render_bookmark_actions },
],
buttons: [
{
extend: 'colvis',
columns: '.colVisToggled'
extend: 'colvis'
}
],
responsive: true,
Expand Down Expand Up @@ -162,11 +158,9 @@ <h1>{{ book.title }}</h1>
}

let render_bookmark_actions = function(data, type, row, meta) {
// TODO zzfuture fix: security - add CSRF token

const links = [];
const make_link = function(label, func) {
const s = `<a href="#" data-bookmark_id="${row[2]}" data-title="${row[1]}" onclick="${func}(this)">${label}</a>`;
const s = `<a href="#" data-bookmark_id="${row['TbID']}" data-title="${row['TbTitle']}" onclick="${func}(this)">${label}</a>`;
links.push(s);
};

Expand All @@ -179,8 +173,8 @@ <h1>{{ book.title }}</h1>
};

const render_page_link = function(data, type, row, meta) {
page_num = row[0];
return `<a href=/read/{{book.id}}/page/${page_num}>${row[1]}</a>`
page_num = row['TxOrder'];
return `<a href=/read/{{book.id}}/page/${page_num}>${row['TbTitle']}</a>`
}

/**
Expand Down
52 changes: 17 additions & 35 deletions lute/templates/term/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -107,15 +107,6 @@

<script>

// Column indexes returned in the datatables json.
const WORD_COL = 1;
const TRANSLATION_COL = 3;
const CREATED_DATE_COL = 7;
const WID_COL = 8;
const LID_COL = 9;
const IMG_COL = 10;
const STATUS_TEXT_COL = 13;

let setup_term_datatable = function(initial_search) {
var table = $('#termtable').DataTable({
layout: {
Expand Down Expand Up @@ -150,26 +141,17 @@
className: 'row-selected'
},
search: { search: initial_search },
columnDefs: [
// "chk" is included in the underlying SQL query.
// Without it, datatables would place the values
// in the wrong table columns. Ugly hack, but works.
{ name: "chk", targets: 0, searchable: false, orderable: false, data: null, render: render_checkbox },
{ name: "WoText", targets: WORD_COL, render: render_text },
{ name: "ParentText", targets: 2 },
{ name: "WoTranslation", targets: TRANSLATION_COL, width: "40%", searchable: true, render: render_translation },
{ name: "LgName", targets: 4 },
{ name: "TagList", targets: 5 },
{ name: "StID", targets: 6, render: render_status },
{ name: "WoCreated", targets: CREATED_DATE_COL, render: render_date_created },

{ name: "WoID", targets: WID_COL, visible: false },
{ name: "LgID", targets: LID_COL, visible: false },
{ name: "WiSource", targets: IMG_COL, visible: false },
{ name: "StAbbreviation", targets: 11, visible: false },
{ name: "SyncStatus", targets: 12, visible: false },
{ name: "StText", targets: STATUS_TEXT_COL, visible: false },
{ name: "WoRomanization", targets: 14, visible: false },
columns: [
{ searchable: false, orderable: false, render: render_checkbox },
{ name: "WoText", render: render_text },
{ name: "ParentText", data: "ParentText" },
{ name: "WoTranslation", width: "40%", searchable: true, render: render_translation },
{ name: "LgName", data: "LgName" },
{ name: "TagList", data: "TagList" },
{ name: "StID", render: render_status },
{ name: "WoCreated", render: render_date_created },
{ name: "WoID", data: "WoID", visible: false },
{ name: "LgID", data: "LgID", visible: false },
],

// Ajax call
Expand Down Expand Up @@ -199,31 +181,31 @@


let render_text = function ( data, type, row, meta ) {
return `<a href="/term/edit/${row[WID_COL]}">${row[WORD_COL]}</a>`;
return `<a href="/term/edit/${row['WoID']}">${row['WoText']}</a>`;
};

// Use the status ID for sorting, so Well Known comes after Learned (5),
// but use the status text ("New (1)") for the cell display.
let render_status = function ( data, type, row, meta ) {
return row[STATUS_TEXT_COL];
return row["StText"];
};

let render_checkbox = function (data, type, row, meta) {
return `<input type="checkbox" class="chkWord" name="wordids" wordid="${row[WID_COL]}" langid="${row[LID_COL]}" onclick="handleChkClick()">`;
return `<input type="checkbox" class="chkWord" name="wordids" wordid="${row['WoID']}" langid="${row['LgID']}" onclick="handleChkClick()">`;
};

let render_translation = function ( data, type, row, meta ) {
let tx = row[TRANSLATION_COL] ?? '';
let tx = row["WoTranslation"] ?? '';
tx = tx.replaceAll("\r\n", "<br />");
let imgsrc = row[IMG_COL] ?? '';
let imgsrc = row["WiSource"] ?? '';
if (imgsrc != '')
imgsrc = `<img class="term-listing-image" style="margin-top: 5px;" src="${imgsrc}" />`;
let ret = [ tx, imgsrc ].filter((s) => s != '');
return ret.join('<br />');
};

let render_date_created = function (data, type, row, meta) {
const dt = row[CREATED_DATE_COL];
const dt = row["WoCreated"];
const datepart = dt.split(' ')[0];
return `<span title="${dt}">${datepart}</span>`;
};
Expand Down
50 changes: 21 additions & 29 deletions lute/templates/termtag/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -37,35 +37,11 @@
processing: true,
serverSide: true,
stateSave: true,
columnDefs: [
{
"name": "TgText", "targets": 0,
"render": function ( data, type, row, meta ) {
return `<a href="/termtag/edit/${row[3]}">${row[0]}</a>`;
}
},
{ "name": "TgComment", "targets": 1 },
{ "name": "TermCount", "targets": 2,
"render": function ( data, type, row, meta ) {
const count = parseInt(row[2]);
if (count == 0)
return '-';
return `<a href="/term/index/${row[0]}">${count}</a>`;
}
},
{
"targets": 3,
"data": null,
"searchable": false,
"orderable": false,
"render": function ( data, type, row, meta ) {
// TODO zzfuture fix: security - add CSRF token
const tgid = row[3];
return `<span id="deltermtag${tgid}" onclick="confirm_delete(${tgid})"><img src="{{ url_for('static', filename='/icn/minus-button.png') }}" title="Delete" /></span>`;
}
},
/* Extra data that is returned in the row for rendering, but not shown. */
{ "name": "TgID", "targets": 4, "data": null, "visible": false }
columns: [
{ name: "TgText", render: render_tag_text },
{ name: "TgComment", data: "TgComment" },
{ name: "TermCount", render: render_term_count },
{ data: null, searchable: false, orderable: false, render: render_delete },
],

// Ajax call
Expand All @@ -79,6 +55,22 @@

} // end setup datatable

let render_tag_text = function ( data, type, row, meta ) {
return `<a href="/termtag/edit/${row['TgID']}">${row['TgText']}</a>`;
}

let render_term_count = function ( data, type, row, meta ) {
const count = parseInt(row['TermCount']);
if (count == 0)
return '-';
return count;
}

let render_delete = function ( data, type, row, meta ) {
// TODO zzfuture fix: security - add CSRF token
const tgid = row['TgID'];
return `<span id="deltermtag${tgid}" onclick="confirm_delete(${tgid})"><img src="{{ url_for('static', filename='/icn/minus-button.png') }}" title="Delete" /></span>`;
}

$(document).ready(function () {
setup_datatable();
Expand Down
2 changes: 1 addition & 1 deletion lute/term/datatables.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ def get_data_tables_list(parameters):
"Term json data for datatables."

base_sql = """SELECT
0 as chk, w.WoID as WoID, LgName, L.LgID as LgID, w.WoText as WoText, parents.parentlist as ParentText, w.WoTranslation,
w.WoID as WoID, LgName, L.LgID as LgID, w.WoText as WoText, parents.parentlist as ParentText, w.WoTranslation,
w.WoRomanization,
replace(wi.WiSource, '.jpeg', '') as WiSource,
ifnull(tags.taglist, '') as TagList,
Expand Down
Loading

0 comments on commit 74342c5

Please sign in to comment.