![]() |
#1 |
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 12,336
Karma: 8012652
Join Date: Jan 2010
Location: Notts, England
Device: Kobo Libra 2
|
[Kobo] Collections: using a template
@davidfor: last we talked about this I was playing with using a template to optionally rewrite collection names. You felt that a better approach would be to use a template to generate the names, not rewrite the names. After a month or so of using my original system I came to agree with you.
I have an implementation that permits one to add "template" to the list of collection attributes. It can be the only attribute if you wish. The driver invokes the template when looping through the collection attributes. The template returns a list of collection names separated by '#@#' (the same separator used in template searches). Here is the template I am now using. It supports both my wife's and my Libra 2s. All the hard work is done in the generate_values() function. For my Libra 2 the template generates two sets of collection names, one set for my personal tags all prefixed with "CBHTags: ", and another set of the author's name's first letter prefixed by 'Authors: '. For my wife's it generates one set of names from her personal tags. Code:
program: globals(serial_number='N4181B1027108'); def generate_values(previous, col_val, sep, prefix, letters): res = ''; for f in col_val separator sep: f = re(f, '^\s*(.*)\s*$', '\1'); if f then if letters then f = substr(f, 0, letters) fi; res = ':@:' & prefix & f fi rof; return previous & res fed; if serial_number == 'N4181B1027108' then res = generate_values('', $authors, '&', 'Authors: ', 1); res = generate_values(res, $#cbhtags, ',', 'CBHTags: ', ''); return res fi; if serial_number == 'N4181B5019336' then return generate_values('', $#dthtags, ',', 'DTH_Tags: ', '') fi There are two reasons I chose to add "template" as a collections attribute instead of making it either attributes or template but not both:
|
![]() |
![]() |
![]() |
#2 |
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 24,905
Karma: 47303824
Join Date: Jul 2011
Location: Sydney, Australia
Device: Kobo:Touch,Glo, AuraH2O, GloHD,AuraONE, ClaraHD, Libra H2O; tolinoepos
|
I've gone back and forth over exactly how to do this. My original thought was either a template or the current list of columns. But, allowing both is probably the most compatible. Which is the way you are doing it. But, I'm not a fan of adding what is effectively a special column name. I would normally add a checkbox to enable the feature and that would be enough.
Can I get a copy of your code? That should save me some time, at least for a quick test to make sure I have understood what you are doing. |
![]() |
![]() |
Advert | |
|
![]() |
#3 | ||
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 12,336
Karma: 8012652
Join Date: Jan 2010
Location: Notts, England
Device: Kobo Libra 2
|
Quote:
One problem with that is the interplay between the contents of the columns box and metadata management. If you use a checkbox then can I also use the columns box? What if I don't, making the columns box empty, which in the current code would prevent get_collections() from being called. Is using the checkbox equivalent to having "something" in the columns box? It also raises the question "What does the template return?" Is it a list of columns or a list of items? Finally, how does one solve the problem of two users wanting different metadata management settings? That could be done with a checkbox and yet another template that returns the management setting desired for the connected device. I have been tempted to play with this, but as I don't need it I haven't taken the time. The "special name" is safe because it can't conflict with a custom column. It could be made safer by using something like "%template" instead of "template". But you know all the above. Quote:
The source files incorporate all your changes that have been checked in by Kovid. |
||
![]() |
![]() |
![]() |
#4 | |||||
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 24,905
Karma: 47303824
Join Date: Jul 2011
Location: Sydney, Australia
Device: Kobo:Touch,Glo, AuraH2O, GloHD,AuraONE, ClaraHD, Libra H2O; tolinoepos
|
Quote:
Quote:
Quote:
Quote:
Quote:
|
|||||
![]() |
![]() |
![]() |
#5 | ||
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 12,336
Karma: 8012652
Join Date: Jan 2010
Location: Notts, England
Device: Kobo Libra 2
|
Quote:
I have most of the implementation to permit overriding metadata management with a template. See the screen capture. If you wish I can forward it when the implementation is finished. FWIW: I have added a new formatter function that I have wanted for some time, list_join(). It simplified dealing with generating the item list. Here are the details. Quote:
Last edited by chaley; 04-25-2022 at 07:16 AM. Reason: Fixed separator |
||
![]() |
![]() |
Advert | |
|
![]() |
#6 |
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 24,905
Karma: 47303824
Join Date: Jul 2011
Location: Sydney, Australia
Device: Kobo:Touch,Glo, AuraH2O, GloHD,AuraONE, ClaraHD, Libra H2O; tolinoepos
|
Having said all that, which took all day as I was doing other things and writing the code. So...
Attached is my version of using templates for collections. It is inspired (I think that's the best word) by your code. Things it does:
I have done some testing, but nowhere near enough. It seems to work with the different combinations of the options. And the collection template I have been using is: Code:
program: globals(serial_number='N7828A0018128'); collections = ''; if serial_number == 'N7828A0018128' then collections = connected_device_name('main') fi; if (connected_device_uuid("main") == '30c617bc-d1e4-4cc0-bc69-ef7ca6ab88c9') then collections = list_union(collections, 'connected_device_uuid', ',') fi; return collections ![]() |
![]() |
![]() |
![]() |
#7 |
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 12,336
Karma: 8012652
Join Date: Jan 2010
Location: Notts, England
Device: Kobo Libra 2
|
I tried your code and with 3 changes it works for me.
The first change is in the driver. I have no collections attributes. However, the check used an 'and' where I think you want an 'or' because it required me to define some. The second is in books. Because of how python handles references, collections_attributes had %template% appended to it for each book. That caused the template to be executed more than once per book The third is in books. For the reasons I mentioned above, I can't use comma as the template separator (my authors are LN, FN). I changed it to what I was using, ':@:' The files are attached. |
![]() |
![]() |
![]() |
#8 |
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 12,336
Karma: 8012652
Join Date: Jan 2010
Location: Notts, England
Device: Kobo Libra 2
|
FYI: Here is a mostly equivalent template to the one in post #1, using the new list_join() function. It is much simpler. Not to say it is simple, but simpler.
Code:
program: globals(serial_number='N4181B5019336'); if serial_number == 'N4181B1027108' then return list_join( ':@:', list_re($#cbhtags, ',', '^(.*)$', 'CBH Tags: \1'), ',', list_re($authors, '&', '(^.).*', 'Authors: \1'), '&') fi; if serial_number == 'N4181B5019336' then return list_join( ':@:', list_re($#dthtags, ',', '^(.*)$', 'DTH Tags: \1'), ',', list_re($authors, '&', '(^.*)', 'Authors: \1'), '&') fi The second 'if' block shows why comma can't be the separator. We both like to see authors in LN, FN format. The full author names contain commas and would be split into two collection items. Why not use the standard Kobo author list? Neither of us like that list because it isn't sorted by the first letter you see on the line. I have to scan the line for the last name to figure out where I am. The pattern for an unmodified calibre column is: Code:
program: return list_join(':@:', $column_name, ',') Code:
program: return list_join(':@:', $tags, ',', $publisher, ',') |
![]() |
![]() |
![]() |
#9 |
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 12,336
Karma: 8012652
Join Date: Jan 2010
Location: Notts, England
Device: Kobo Libra 2
|
A thought: you could 'solve' the separator problem by providing a box where the user can choose whatever separator is appropriate. It would default to comma, which would cover (I think) the majority of uses. Something like the following:
The user (me) would change it if values contain commas, which can happen for authors-like columns and single-value columns like publisher, series, enums, and non-tags text. On the other hand, having a choice means one must understand when to choose. Maybe it is better to have a rule, not a choice. ![]() |
![]() |
![]() |
![]() |
#10 | |||
Grand Sorcerer
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 24,905
Karma: 47303824
Join Date: Jul 2011
Location: Sydney, Australia
Device: Kobo:Touch,Glo, AuraH2O, GloHD,AuraONE, ClaraHD, Libra H2O; tolinoepos
|
Quote:
Quote:
Quote:
I have checked the code in and created a pull request. I think I included all your changes. And then I noticed Kovid had created a new release. Is the weekend coming early? |
|||
![]() |
![]() |
![]() |
Thread Tools | Search this Thread |
|
![]() |
||||
Thread | Thread Starter | Forum | Replies | Last Post |
Template: saving template tester when restarting Calibre | ownedbycats | Library Management | 14 | 03-29-2021 05:57 PM |
Kobo.conf template? | Uncle Robin | Kobo Reader | 8 | 08-18-2020 10:08 AM |
save template and collections/folders | 2nise | Library Management | 4 | 10-09-2019 10:01 AM |
Glo Preventing Kobo Glo syncing Collections with Kobo | Ferretqueen | Kobo Reader | 4 | 09-30-2016 10:56 PM |
Kobo DVD Case - Insert Template | clintbradford | Kobo Reader | 17 | 08-20-2010 04:36 PM |