Compare commits

...

7 Commits

Author SHA1 Message Date
Guilhem Fauré
55e19d4825 up version 2023-06-23 16:47:17 +02:00
Guilhem Fauré
b245ff75c5 option to rename taxonomies 2023-06-23 15:11:01 +02:00
Guilhem Fauré
8769185b8d proper taxonomy management, no more tags only 2023-06-23 11:47:22 +02:00
Guilhem Fauré
164a1e8228 tags conversion 2023-06-23 11:14:14 +02:00
Guilhem Fauré
3cc90f6dc2 fixed tags, use translated description instead of id 2023-06-23 11:12:40 +02:00
Guilhem Fauré
00f3ed6cf9 added static images 2023-06-23 09:59:30 +02:00
Guilhem Fauré
3ab94aa388 add tags IDs 2023-06-23 09:34:37 +02:00
4 changed files with 97 additions and 13 deletions

View File

@ -106,6 +106,9 @@ prepend_h1: false # Add title of articles as Markdown h1, looks better on certai
# dest: title
# repr: "{} _" # (this is the default repr)
move_fields: []
# Some taxonomies (Spip Mots types) to not export, typically specific to Spip functions
ignore_taxonomies: ["Gestion du site", "Gestion des articles", "Mise en page"]
rename_taxonomies: { equipes: "tag-equipes" } # Rename taxonomies (prenvent conflict)
# Ignored data settings
export_drafts: true # Should we export drafts

View File

@ -1,6 +1,6 @@
[tool.poetry]
name = "spip2md"
version = "0.1.0"
version = "0.1.1"
description = "Generate a static website with plain Markdown+YAML files from a SPIP CMS database"
license = "GPL-2.0"

View File

@ -72,6 +72,8 @@ class Configuration:
export_drafts: bool = True # Should we export drafts as draft:true articles
export_empty: bool = True # Should we export empty articles
remove_html: bool = True # Should spip2md remove every HTML tags
ignore_taxonomies = ("Gestion du site", "Gestion des articles", "Mise en page")
rename_taxonomies: dict[str, str] = {"equipes": "tag-equipes"}
metadata_markup: bool = False # Should spip2md keep the markup in metadata fields
title_max_length: int = 40 # Maximum length of a single title for directory names
unknown_char_replacement: str = "??" # Replaces unknown characters

View File

@ -52,6 +52,8 @@ from spip2md.spip_models import (
SpipAuteursLiens,
SpipDocuments,
SpipDocumentsLiens,
SpipMots,
SpipMotsLiens,
SpipRubriques,
)
from spip2md.style import BOLD, CYAN, GREEN, WARNING_STYLE, YELLOW, esc
@ -61,6 +63,9 @@ DeepDict = dict[str, "list[DeepDict] | list[str] | str"]
# Define logger for this files logs
LOG = logging.getLogger(NAME + ".models")
# Define type that images can have
IMG_TYPES = ("jpg", "png", "jpeg", "gif", "webp", "ico")
class SpipWritable:
# From SPIP database
@ -349,8 +354,10 @@ class SpipRedactional(SpipWritable):
langue_choisie: str
# Converted
_text: str
_taxonomies: dict[str, list[str]] = {}
_url_title: str # Title in metadata of articles
_parenturl: str # URL relative to lang to direct parent
_static_img_path: Optional[str] = None # Path to the static img of this article
# Get rid of other lang than forced in text and modify lang to forced if found
def translate_multi(
@ -372,6 +379,9 @@ class SpipRedactional(SpipWritable):
self.lang = forced_lang # So write-all will not be cancelled
# Replace the mutli blocks with the text in the proper lang
text = text.replace(block.group(), lang.group(1))
else:
# Replace the mutli blocks with the text inside
text = text.replace(block.group(), block.group(1))
if lang is None:
LOG.debug(f"{forced_lang} not found in `{self._url_title}`")
return text
@ -563,6 +573,37 @@ class SpipRedactional(SpipWritable):
LOG.debug(f"Apply conversions to {self.lang} `{self._url_title}` extra")
self._extra = self.convert_field(self._extra, CFG.metadata_markup)
def convert_taxonomies(self, forcedlang: str) -> None:
self._taxonomies = {}
for tag in self.taxonomies():
taxonomy = str(tag.type)
if taxonomy not in CFG.ignore_taxonomies:
LOG.debug(
f"Translate taxonomy of `{self._url_title}`:{tag.descriptif}"
)
if taxonomy in CFG.rename_taxonomies:
LOG.debug(
f"Rename taxonomy {taxonomy}:{CFG.rename_taxonomies[taxonomy]}"
)
taxonomy = CFG.rename_taxonomies[taxonomy]
if str(taxonomy) in self._taxonomies:
self._taxonomies[taxonomy].append(
self.convert_field(
self.translate_multi(forcedlang, str(tag.descriptif), False)
)
)
else:
self._taxonomies[taxonomy] = [
self.convert_field(
self.translate_multi(forcedlang, str(tag.descriptif), False)
)
]
LOG.debug(
f"After translation, taxonomies of `{self._url_title}`:{self._taxonomies}"
)
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
# Initialize converted fields, beginning with underscore
@ -626,6 +667,28 @@ class SpipRedactional(SpipWritable):
body += "\n\n# EXTRA\n\n" + self._extra
return body
def authors(self) -> tuple[SpipAuteurs, ...]:
LOG.debug(f"Initialize authors of `{self._url_title}`")
return (
SpipAuteurs.select()
.join(
SpipAuteursLiens,
on=(SpipAuteurs.id_auteur == SpipAuteursLiens.id_auteur),
)
.where(SpipAuteursLiens.id_objet == self._id)
)
def taxonomies(self) -> tuple[SpipMots, ...]:
LOG.debug(f"Initialize taxonomies of `{self._url_title}`")
return (
SpipMots.select()
.join(
SpipMotsLiens,
on=(SpipMots.id_mot == SpipMotsLiens.id_mot),
)
.where(SpipMotsLiens.id_objet == self._id)
)
# Write all the documents of this object
def write_children(
self,
@ -697,19 +760,40 @@ class SpipRedactional(SpipWritable):
# Write the content of this object into a file named as self.filename()
with open(self.dest_path(), "w") as f:
f.write(self.content())
# Write the eventual static image of this object
if self._static_img_path:
copyfile(
self._static_img_path,
self.dest_directory() + basename(self._static_img_path),
)
return self.dest_path()
# Append static images based on filename instead of DB to objects texts
def append_static_images(self, obj_str: str = "art", load_str: str = "on"):
for t in IMG_TYPES:
path: str = CFG.data_dir + obj_str + load_str + str(self._id) + "." + t
LOG.debug(f"Search static image of `{self._url_title}` at: {path}")
if isfile(path):
LOG.debug(f"Found static image of `{self._url_title}` at: {path}")
# Append static image to content
self._text += f"\n\n![]({basename(path)})"
# Store its path to write it later
self._static_img_path = path
break
# Apply post-init conversions and cancel the export if self not of the right lang
def convert(self, forced_lang: str) -> None:
self.convert_title(forced_lang)
self.convert_text(forced_lang)
self.convert_extra()
self.convert_taxonomies(forced_lang)
if self.lang != forced_lang:
raise LangNotFoundError(
f"`{self._url_title}` lang is {self.lang} instead of the wanted"
+ f" {forced_lang} and it dont contains"
+ f" {forced_lang} translation in Markup either"
)
self.append_static_images()
class Article(SpipRedactional, SpipArticles):
@ -741,7 +825,9 @@ class Article(SpipRedactional, SpipArticles):
}
# Add debugging meta if needed
if CFG.debug_meta:
meta = meta | {"spip_id_rubrique": self.id_rubrique}
meta |= {"spip_id_rubrique": self.id_rubrique}
if self._taxonomies:
meta |= self._taxonomies
if append is not None:
return super().frontmatter(meta | append)
else:
@ -760,17 +846,6 @@ class Article(SpipRedactional, SpipArticles):
body += "\n\n# MICROBLOGGING\n\n" + self._microblog
return body
def authors(self) -> list[SpipAuteurs]:
LOG.debug(f"Initialize authors of `{self._url_title}`")
return (
SpipAuteurs.select()
.join(
SpipAuteursLiens,
on=(SpipAuteurs.id_auteur == SpipAuteursLiens.id_auteur),
)
.where(SpipAuteursLiens.id_objet == self._id)
)
# Perform all the write steps of this object
def write_all(
self,
@ -853,3 +928,7 @@ class Section(SpipRedactional, SpipRubriques):
"articles": self.write_children(self.articles(), forced_lang),
"sections": self.write_children(self.sections(), forced_lang),
}
# Append static images based on filename instead of DB to objects texts
def append_static_images(self, obj_str: str = "rub", load_str: str = "on"):
super().append_static_images(obj_str, load_str)