add default user image

This commit is contained in:
tcprod 2026-03-21 17:20:59 +01:00
parent 64343b696f
commit 63df4b7edd
6 changed files with 75 additions and 61 deletions

11
config.toml Normal file
View File

@ -0,0 +1,11 @@
[database]
db_user="demo_user"
db_password="demo_password"
db_host="127.0.0.1"
db_port=3306
db_name="ezgg_lan_manager"
[badge_generator]
browser_path="C:/Program Files/Google/Chrome/Application/chrome.exe" # Do not forget to change
svg_template="template/template_dynamic_name_size.svg"
html_template="template/template_badge_180_rotated.html"
default_user_image="template/default_user_image.png"

View File

@ -2,23 +2,18 @@ import asyncio
from services.DatabaseService import DatabaseService from services.DatabaseService import DatabaseService
from services.BadgeGeneratorService import BadgeGeneratorService from services.BadgeGeneratorService import BadgeGeneratorService
from pathlib import Path
async def main(): async def main():
db = DatabaseService("sql_config.toml") db = DatabaseService("config.toml")
await db.init_db_pool() await db.init_db_pool()
badges = await db.get_user_badges() badges = await db.get_user_badges()
badge_generator = BadgeGeneratorService( badge_generator = BadgeGeneratorService("config.toml")
svg_template=Path("template/template_dynamic_name_size.svg"),
html_template=Path("template/template_badge_180_rotated.html"),
chrome_path=Path(r"C:\Program Files\Google\Chrome\Application\chrome.exe")
)
for user_badge in badges: for user_badge in badges:
badge_generator.generate_badge( badge_generator.generate_badge(
name=user_badge["user_name"], user_name=user_badge["user_name"],
seat_id=user_badge["seat_id"], seat_id=user_badge["seat_id"],
picture=user_badge["picture"] picture=user_badge["picture"]
) )

View File

@ -1,74 +1,79 @@
import logging
import os
import re
import base64 import base64
import logging
import re
import subprocess import subprocess
import tempfile import tomllib
from pathlib import Path from pathlib import Path
from jinja2 import Environment, FileSystemLoader
logging.basicConfig( from jinja2 import Environment, FileSystemLoader
level=logging.INFO,
format="%(asctime)s [%(levelname)s] %(name)s: %(message)s"
)
logger = logging.getLogger(__name__.split(".")[-1]) logger = logging.getLogger(__name__.split(".")[-1])
def get_default_user_image(image_path: Path) -> str:
with open(image_path, "rb") as file:
encoded_bytes = base64.b64encode(file.read())
return encoded_bytes.decode("utf-8")
class BadgeGeneratorService: class BadgeGeneratorService:
def __init__(self, svg_template: Path, html_template: Path, chrome_path: Path): def __init__(self, config: str):
self.svg_template = svg_template with open(config, "rb") as file:
self.html_template = html_template config = tomllib.load(file)
self.chrome_path = chrome_path
def generate_badge(self, name, seat_id, picture) -> None: self.bg_config = config["badge_generator"]
svg = self._get_svg(name, seat_id, picture) self.env = Environment(loader=FileSystemLoader("template"))
html = self._svg_to_html(svg)
self._html_to_pdf(html, f"output_badges/{name}.pdf")
logger.info(f"Created: {name}, {seat_id}, {str(picture)[:10]}")
def _get_svg(self, username: str, seat: str, image_base64: bytes) -> str: self.svg_template = self.env.get_template(Path(self.bg_config["svg_template"]).name)
env = Environment(loader=FileSystemLoader("template")) self.html_template = self.env.get_template(Path(self.bg_config["html_template"]).name)
template = env.get_template(self.svg_template.name) self.browser_path = Path(self.bg_config["browser_path"])
if image_base64: self.default_image = get_default_user_image(Path(self.bg_config["default_user_image"]))
image_base64 = base64.b64encode(image_base64).decode("utf-8") self._badge_count = 0
def _get_user_svg(self, user_name: str, seat_id: str, user_image: bytes) -> str:
if user_image:
user_image = base64.b64encode(user_image).decode("utf-8")
else: else:
image_base64 = "Standard picture" user_image = self.default_image
svg = template.render( svg = self.svg_template.render(
picture=image_base64, picture=user_image,
username=username, username=user_name,
seat_id=seat seat_id=seat_id
) )
return svg return svg
def _svg_to_html(self, svg: str) -> str: def _get_html_from_svg(self, user_svg: str) -> str:
width = re.search(r'width="([^"]+)"', svg).group(1) width = re.search(r'width="([^"]+)"', user_svg).group(1)
height = re.search(r'height="([^"]+)"', svg).group(1) height = re.search(r'height="([^"]+)"', user_svg).group(1)
env = Environment(loader=FileSystemLoader("template")) html = self.html_template.render(
template = env.get_template(self.html_template.name)
html = template.render(
width=width, width=width,
height=height, height=height,
svg=svg svg=user_svg
) )
return html return html
def _html_to_pdf(self, html: str, pdf: str): def _html_to_pdf(self, user_html: str, output_path: Path) -> None:
with tempfile.NamedTemporaryFile(delete=False, suffix=".html", mode="w", encoding="utf-8") as file: html_path = output_path.with_suffix(".html")
file.write(html)
html_path = file.name html_path.write_text(user_html, encoding="utf-8")
try: try:
subprocess.run([ subprocess.run([
self.chrome_path, self.browser_path,
"--headless", "--headless",
"--disable-gpu", "--disable-gpu",
f"--print-to-pdf={os.path.abspath(pdf)}", f"--print-to-pdf={output_path.resolve()}",
html_path html_path.resolve()
], check=True) ], check=True)
finally: finally:
os.remove(html_path) html_path.unlink(missing_ok=True)
def generate_badge(self, user_name, seat_id, picture) -> None:
svg = self._get_user_svg(user_name, seat_id, picture)
html = self._get_html_from_svg(svg)
output_path = Path(f"output_badges/{user_name}.pdf")
self._html_to_pdf(html, output_path)
self._badge_count += 1
logger.info(f"({self._badge_count}) Created: {output_path}, {user_name}, {seat_id}, {str(picture)[:10]}")

View File

@ -1,12 +1,14 @@
import logging
import tomllib import tomllib
import aiomysql import aiomysql
from typing import Optional from typing import Optional
logger = logging.getLogger(__name__.split(".")[-1])
class DatabaseService: class DatabaseService:
def __init__(self, config: str):
def __init__(self, sql_config: str): with open(config, "rb") as f:
with open(sql_config, "rb") as f:
config = tomllib.load(f) config = tomllib.load(f)
self.db_config = config["database"] self.db_config = config["database"]
@ -23,6 +25,7 @@ class DatabaseService:
maxsize=40, maxsize=40,
autocommit=True autocommit=True
) )
logger.info("Connected to database.")
async def get_user_badges(self) -> list: async def get_user_badges(self) -> list:
async with self._pool.acquire() as conn: async with self._pool.acquire() as conn:

View File

@ -0,0 +1,6 @@
import logging
logging.basicConfig(
level=logging.INFO,
format="%(asctime)s [%(levelname)s] %(name)s: %(message)s"
)

View File

@ -1,6 +0,0 @@
[database]
db_user="demo_user"
db_password="demo_password"
db_host="127.0.0.1"
db_port=3306
db_name="ezgg_lan_manager"