Experimented around with Calibre's database API as mentioned
here and managed to set up a little CLI plugin to pull read percentage and last read time from a folder full of KOreader metadata into Calibre.
Code:
import os
import datetime
from dateutil.tz import tzlocal
from calibre.customize import Plugin
from calibre.library import db
class KoreaderPercentSync(Plugin):
name = 'KOreader Percent Sync'
description = 'Sync KOReader Percentage from command line'
supported_platforms = ['windows', 'osx', 'linux']
author = 'Orange'
version = (0, 0, 3)
minimum_calibre_version = (0, 7, 53)
def cli_main(self, args):
target = args[1]
database = db(args[2]).new_api
to_update_percent, to_update_date = {}, {}
for root, dirs, files in os.walk(target):
for target_folder in dirs:
book = int(target_folder[:-4].rpartition(" - ")[2])
calibre_percent = database.field_for("#perc_read", book)
if calibre_percent != 1:
percent, date = parse_metadata(os.path.join(root, target_folder, "metadata.epub.lua"))
if not calibre_percent or abs(calibre_percent - percent) > 0.00001:
to_update_percent[book] = percent
to_update_date[book] = date
database.set_field("#perc_read", to_update_percent)
database.set_field("#last_read", to_update_date)
def parse_metadata(meta_file):
with open(meta_file, "r") as metadata:
percent = 0
date = datetime.datetime.fromtimestamp(os.path.getmtime(meta_file), tzlocal())
for line in metadata:
read_line = line.strip()
if read_line.startswith("[\"percent_finished\"]"):
percent = read_line[23:-1]
elif read_line == "[\"status\"] = \"complete\"":
return (1, date)
return (float(percent), date)
Works as a command line plugin taking two arguments for KOReader files & Calibre library location. For now expects files are named with the calibre ID at the end of the file/folder name separated by " - ". .txt files with timestamp no longer needed since I finally figured a way to move the files to my PC from my e-reader without messing with the timestamps on the files themselves...