|
|
#46 |
|
Zealot
![]() Posts: 104
Karma: 40
Join Date: Mar 2020
Location: Belgium (sorry, I am from the Walloon side of the country and I speak french only)
Device: PW3, Kobo Libra H2O
|
I did modify and upload version 1.0.0.
This version provide an adapted algorithm for parse_rating after Babelio.com change |
|
|
|
|
|
#47 |
|
Junior Member
![]() Posts: 3
Karma: 10
Join Date: Jun 2016
Location: France
Device: Kobo Aura H2O Edition 2 v1
|
Hello,
Thank you for this work. Unfortunately, I can't get the grades. Message from Calibre (in French): calibre, version 8.13.0 Babelio Notes: Recherche des Notes et des Votes sur le site Babelio pour 1 livre dont 0 ligne est marquée comme non mise à jour Titre : La Maison des silences Auteur(s) ['Donato Carrisi']: Accès à https://www.babelio.com/livres/Carri...lences/1883375 babelio.com semble ne pas avoir des votes et/ou des notes distribution dans le temps des accès à babelio.com Sat Oct 18 18:55:27 2025 accès à https://www.babelio.com/livres/Carri...lences/1883375 Thank you |
|
|
|
| Advert | |
|
|
|
|
#48 |
|
Junior Member
![]() Posts: 3
Karma: 10
Join Date: Jun 2016
Location: France
Device: Kobo Aura H2O Edition 2 v1
|
**** Correction to the previous message sent too quickly: I hadn't updated the Babelio Notes plugin.
After updating both Babelio plugins, everything works fine. Sorry, and thanks again. |
|
|
|
|
|
#49 |
|
Zealot
![]() Posts: 104
Karma: 40
Join Date: Mar 2020
Location: Belgium (sorry, I am from the Walloon side of the country and I speak french only)
Device: PW3, Kobo Libra H2O
|
|
|
|
|
|
|
#50 |
|
Enthusiast
![]() Posts: 33
Karma: 10
Join Date: Feb 2023
Device: Kindle Oasis 3 / Kobo Libra 2
|
Bonjour,
Ca ne fonctionne plus depuis quelques temps, que je copie le babelio_id manuellement ou que je laisse le champs vide. Voici les logs: https://www.pastebin.fr/019c24d1-129...a-b4c6d2acbaa7 |
|
|
|
| Advert | |
|
|
|
|
#51 | |
|
Junior Member
![]() Posts: 2
Karma: 10
Join Date: Feb 2026
Device: ipad
|
Quote:
fait un rollback vers la version calibre-64bit-8.16.2 et ca fonctionne de nouveau... un grand merci pour ce plugin mais est-ce qu il serait possible que si on fournit l'isbn ou le babelio_id -> le plugin fetch direct les info sans regarder le reste? |
|
|
|
|
|
|
#52 |
|
Connoisseur
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 80
Karma: 24492
Join Date: Jul 2013
Location: France
Device: Kindle 4, PBk Lux 2, PBk Lux 3, K Aura, K Libra H2O, K Libra2
|
Salut,
j'ai corrigé le plugin, ça fonctionne chez moi en tout cas sur Calibre 9.1. je ne sais pas si je pouvais, si jamais ça pose problème je le retire. slts, Druss67 |
|
|
|
|
|
#53 |
|
Zealot
![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() ![]() Posts: 137
Karma: 10280
Join Date: Oct 2016
Device: none
|
Merci druss67, fonctionne aussi avec la V9.1
|
|
|
|
|
|
#54 | |
|
Zealot
![]() Posts: 104
Karma: 40
Join Date: Mar 2020
Location: Belgium (sorry, I am from the Walloon side of the country and I speak french only)
Device: PW3, Kobo Libra H2O
|
J'y travaille...
Quote:
Code:
bbl_comments = bbl_comments.encode('ascii','xmlcharrefreplace') # et on serialize le tout
la solution présentée par druss67: Code:
bbl_comments = bbl_comments.encode('ascii', errors='xmlcharrefreplace').decode('ascii') # serialize (bs4.encode signature changed; keep safe ASCII HTML)
Je vais voir ce que je peux faire, d'autant que le même problème s'est développé (pour la même raison) pour le plugin de noosfere... Réparé: plutôt que de sérialiser avec un encode, j'ai utilisé str pour le même résultat compatible avec calibre versions 9 et plus anciennes, Code:
bbl_comments = str(bbl_comments) Last edited by lrpirlet; 02-06-2026 at 11:51 AM. Reason: corrigé |
|
|
|
|
|
|
#55 |
|
Member
![]() Posts: 15
Karma: 10
Join Date: Sep 2021
Device: Kobo
|
Salut salut,
Il y a un nouveau soucis avec babelio mais je ne suis pas sur qu'il y ait une solution... En gros, dès que j'utilise le plugin je suis ban de babelio. J'étais ban hier. Tout à l'heure, j'ai pu accéder au site, donc j'ai tenté de récupérer quelques métadonnées et j'ai été de bouveau ban instanément. Si de tente d'ouvrir babelio en utilisant le wifi de mon tel, ça fonctionne. J'obtiens désormais : ERR_CONNECTION_TIMED_OUT.... ![]() Spoiler:
Je suis le seul à qui ça arrive ? Va falloir se tourner vers booknode ![]() Edit : j'ai récupéré l'accès à Babelio, j'ai renseigné manuellement le babelio_id avant, j'ai lancé une seule récupération de métadonnée et je suis de nouveau ban. Last edited by unbreak51; 03-23-2026 at 07:32 PM. |
|
|
|
|
|
#56 | ||
|
Zealot
![]() Posts: 104
Karma: 40
Join Date: Mar 2020
Location: Belgium (sorry, I am from the Walloon side of the country and I speak french only)
Device: PW3, Kobo Libra H2O
|
Désolé C'est la politique de Babelio
Quote:
C'est un choix de Babelio... Peut être refusent ils de répondre quand la pub n'est pas publiée.... De nouveau, c'est leur choix et ils assument les conséquences. En ce qui me concerne, Babelio n'existe plus. SI VRAIMENT, j'ai besoin de renseignement sur un bouquin, j'y vais en mode interactif, je copie/paste les infos dont j'ai besoin... Mais j'ai tendance a voir ailleur. Quote:
|
||
|
|
|
|
|
#57 |
|
Member
![]() Posts: 15
Karma: 10
Join Date: Sep 2021
Device: Kobo
|
C'était quand même bien pratique le plugin ... C'est triste.
|
|
|
|
|
|
#58 | |
|
Junior Member
![]() Posts: 2
Karma: 10
Join Date: Feb 2026
Device: ipad
|
aide via l'IA...
Quote:
![]() j'ai poussé le truc un peu plus loin pour moins m'embêter ![]() -> https://aistudio.google.com/prompts/new_chat je lui donne le prompt suivant: here is a python script, please load it so i can use it for the next prompt: Code:
import os
import re
import json
import requests
import concurrent.futures
from google import genai
from google.genai import types
# ==============================================================================
# CONFIGURATION (Edit these values)
# ==============================================================================
GEMINI_API_KEY = "xxx"
MODEL_NAME = "gemma-4-26b-a4b-it" # Fast and cost-efficient
SYSTEM_INSTRUCTION = (
"You are a professional librarian specialized in French literature. "
"Your task is to identify books from text and provide accurate metadata in JSON format. "
"Always prioritize 13-digit ISBNs and French edition details."
)
TARGET_DIR = r'D:\book\rename'
# Execution Modes:
# - "GENERATE_BAT": Generates a ready-to-use "rename_books.bat" inside TARGET_DIR
# - "LIVE_RENAME": Renames the files directly on your drive
# - "DRY_RUN": Prints what changes would occur without modifying any files
MODE = "GENERATE_BAT"
# Number of parallel workers (5 is usually a safe default to avoid rate limits)
MAX_WORKERS = 5
# Setup Gemini Client (Thread-safe)
client = genai.Client(api_key=GEMINI_API_KEY)
# ==============================================================================
# CORE LOGIC
# ==============================================================================
def validate_book_match(clean_bookname, parsed_data):
"""
Extracts key identifying words from the cleaned filename
and verifies they appear in the AI's resolved target page title.
"""
target_title = str(parsed_data.get("exact_title_on_source_page", "")).lower()
resolved_title = str(parsed_data.get("title", "")).lower()
words = re.findall(r'\b[a-zA-Z]{4,}\b', clean_bookname.lower())
ignored_words = {
"tome", "volume", "french", "edition", "francais", "français",
"epub", "pdf", "book", "t01", "t02", "t03", "t04", "t05", "cbz"
}
keywords = [w for w in words if w not in ignored_words]
if not keywords:
keywords = [w for w in re.findall(r'\b[a-zA-Z]{3,}\b', clean_bookname.lower()) if w not in ignored_words]
if not keywords:
return True
for kw in keywords:
if kw in target_title or kw in resolved_title:
return True
return False
def query_llm(filename):
"""Sends the text to Gemini and attempts to extract JSON."""
prompt = f"""
do a websearch and Identify the book: "{filename}" (French Edition).
1. Search for the official series title and author.
2. Identify the volume/tome number.
3. Search for the 13-digit ISBN specifically (on Amazon.fr).
4. Perform a secondary verification search using only the found ISBN on fnac.com to ensure it resolves strictly to this book and not a different series or volume released by the same publisher on the same date.
5. Extract the literal title as it appears on the Amazon.fr page for the source URL you provide.
Return ONLY a JSON object:
{{
"title": "clean serie title",
"volume": "number or null",
"author": "author name",
"isbn": "13-digit ISBN",
"verified_source": "URL",
"exact_title_on_source_page": "exact text of the book title listed on the verified_source page"
}}
"""
try:
grounding_tool = types.Tool(
google_search=types.GoogleSearch()
)
response = client.models.generate_content(
model=MODEL_NAME,
contents=prompt,
config=types.GenerateContentConfig(
system_instruction=SYSTEM_INSTRUCTION,
temperature=0.0,
tools=[grounding_tool],
response_mime_type="application/json",
),
)
return json.loads(response.text)
except Exception as e:
print(f" [!] Error during API call for {filename}: {e}")
return None
def process_single_file(filename):
"""Processes metadata retrieval and path construction for a single file."""
full_path = os.path.join(TARGET_DIR, filename)
# Extra verification
if os.path.isdir(full_path) or filename.startswith('.'):
return None
# Clean the filename prefixes
bookname = filename
for prefix in ["Zz", "zz", "ZZ"]:
if bookname.startswith(prefix):
bookname = bookname[len(prefix):]
break
# Dynamic extension separation
base_name, extension = os.path.splitext(bookname)
print(f"[*] Started processing: {base_name}")
data = query_llm(base_name)
if data:
if not validate_book_match(base_name, data):
print(f" [!] Safety Validation Failed for: {base_name}")
return None
title = data.get("title")
volume = data.get("volume")
author = data.get("author")
isbn = data.get("isbn")
if not title:
print(f" [!] Missing title in AI result for: {base_name}")
return None
# Format filename
if volume and str(volume).strip().lower() != 'null':
new_name = f"{title} ,tome {volume} - {author} - {isbn}{extension}"
else:
new_name = f"{title}{extension}"
new_name = re.sub(r'[<>:"/\\|?*]', '', new_name)
return {
"old_name": filename,
"new_name": new_name,
"old_path": full_path,
"new_path": os.path.join(TARGET_DIR, new_name)
}
return None
def process_files():
if not os.path.exists(TARGET_DIR):
print(f"Error: The directory '{TARGET_DIR}' does not exist.")
return
print(f"--- Starting Parallel File Processor ---")
print(f"Target: {TARGET_DIR}")
print(f"Mode: {MODE}")
print(f"Model: {MODEL_NAME}")
print(f"Concurrent Workers: {MAX_WORKERS}\n")
# Filter out directories and hidden files
all_files = [f for f in os.listdir(TARGET_DIR)
if os.path.isfile(os.path.join(TARGET_DIR, f)) and not f.startswith('.')]
successful_results = []
# Run the worker functions concurrently
with concurrent.futures.ThreadPoolExecutor(max_workers=MAX_WORKERS) as executor:
futures = {executor.submit(process_single_file, filename): filename for filename in all_files}
for future in concurrent.futures.as_completed(futures):
filename = futures[future]
try:
res = future.result()
if res:
successful_results.append(res)
except Exception as e:
print(f" [!] Error during task execution for {filename}: {e}")
if not successful_results:
print("\n--- No files could be matched/processed. ---")
return
print(f"\n--- Processing Completed ({len(successful_results)} matches resolved) ---")
# Handle output according to chosen mode
if MODE == "DRY_RUN":
for item in successful_results:
if item["old_name"] == item["new_name"]:
print(f" [.] Already cleanly named: '{item['old_name']}'")
else:
print(f" [DRY RUN] Would rename: '{item['old_name']}' -> '{item['new_name']}'")
elif MODE == "LIVE_RENAME":
files_renamed = 0
for item in successful_results:
if item["old_name"] == item["new_name"]:
continue
try:
os.rename(item["old_path"], item["new_path"])
print(f" [SUCCESS] Renamed: '{item['old_name']}' -> '{item['new_name']}'")
files_renamed += 1
except Exception as e:
print(f" [ERROR] Could not rename '{item['old_name']}': {e}")
print(f"Total renamed: {files_renamed}")
elif MODE == "GENERATE_BAT":
bat_path = os.path.join(TARGET_DIR, "rename_books.bat")
try:
with open(bat_path, "w", encoding="utf-8") as f:
f.write("@echo off\n")
f.write("chcp 65001 >nul\n")
f.write(f'cd /d "{TARGET_DIR}"\n\n')
written_count = 0
for item in successful_results:
if item["old_name"] == item["new_name"]:
continue
f.write(f'ren "{item["old_name"]}" "{item["new_name"]}"\n')
written_count += 1
f.write("\necho Renaming completed.\npause\n")
print(f"[SUCCESS] Generated batch file with {written_count} lines at: {bat_path}")
except Exception as e:
print(f"[ERROR] Failed to write batch file: {e}")
if __name__ == "__main__":
process_files()
prompt: now execute the provided script against those files names: j'ai modifié mon calibre (preference / adding book) pour utiliser la même structure (?P<title>.+) - (?P<author>[^_]+) - (?P<isbn>\d+) Du coup, babelio_db fonctionne du tonnerre et rapidement (il a toute la structure + l'isbn valide) |
|
|
|
|
![]() |
|
Similar Threads
|
||||
| Thread | Thread Starter | Forum | Replies | Last Post |
| [Metadata Source Plugin] Comicvine | chewt0y | Plugins | 88 | 07-11-2022 12:00 PM |
| [Metadata Source Plugin] INMONDADORI | Pr.BarnArt | Plugins | 7 | 12-03-2021 12:56 PM |
| Read a book's metadata in a Metadata source plugin? | J-H | Development | 2 | 03-30-2021 09:08 AM |
| [Metadata Source Plugin] Empty Plugin? (Fake Identifier) | mneimeyer | Plugins | 3 | 11-11-2019 08:07 PM |
| [Metadata Source Plugin] LubimyCzytac [PL] | jbienko1 | Plugins | 33 | 01-23-2017 06:15 AM |