feat: work shifts by QR codes
This commit is contained in:
1
generators/work_shifts_qr_code_generator/__init__.py
Normal file
1
generators/work_shifts_qr_code_generator/__init__.py
Normal file
@@ -0,0 +1 @@
|
||||
from .generator import WorkShiftsQRCodeGenerator
|
||||
68
generators/work_shifts_qr_code_generator/generator.py
Normal file
68
generators/work_shifts_qr_code_generator/generator.py
Normal file
@@ -0,0 +1,68 @@
|
||||
import os
|
||||
from io import BytesIO
|
||||
|
||||
from reportlab.pdfgen.canvas import Canvas
|
||||
from reportlab_qrcode import QRCodeImage
|
||||
from reportlab.lib.styles import ParagraphStyle, getSampleStyleSheet
|
||||
from reportlab.lib.units import mm
|
||||
from reportlab.pdfbase import pdfmetrics
|
||||
from reportlab.pdfbase.ttfonts import TTFont
|
||||
from reportlab.platypus import SimpleDocTemplate, Paragraph
|
||||
from sqlalchemy.ext.asyncio import AsyncSession
|
||||
|
||||
from constants import APP_PATH
|
||||
from models import User
|
||||
from services.user import UserService
|
||||
|
||||
|
||||
class WorkShiftsQRCodeGenerator:
|
||||
def __init__(self, session: AsyncSession):
|
||||
self._session = session
|
||||
assets_folder = os.path.join(APP_PATH, 'assets')
|
||||
fonts_folder = os.path.join(assets_folder, 'fonts')
|
||||
font_file_path = os.path.join(fonts_folder, 'DejaVuSans.ttf')
|
||||
self.page_width = 58 * mm
|
||||
self.page_height = 40 * mm
|
||||
pdfmetrics.registerFont(TTFont('DejaVuSans', font_file_path))
|
||||
|
||||
styles = getSampleStyleSheet()
|
||||
self.small_style = ParagraphStyle(
|
||||
'Small',
|
||||
parent=styles['Normal'],
|
||||
alignment=1,
|
||||
fontName='DejaVuSans', # Specify the new font
|
||||
fontSize=9,
|
||||
leading=12,
|
||||
spaceAfter=2,
|
||||
rightIndent=2,
|
||||
)
|
||||
|
||||
def _create_doc(self, buffer):
|
||||
return SimpleDocTemplate(
|
||||
buffer,
|
||||
pagesize=(self.page_width, self.page_height),
|
||||
rightMargin=1,
|
||||
leftMargin=1,
|
||||
topMargin=1,
|
||||
bottomMargin=1
|
||||
)
|
||||
|
||||
async def generate(self, user_id: int) -> BytesIO:
|
||||
buffer = BytesIO()
|
||||
doc = self._create_doc(buffer)
|
||||
|
||||
def on_first_page(canvas: Canvas, doc):
|
||||
qr = QRCodeImage(str(user_id), size=33 * mm)
|
||||
qr.drawOn(canvas, 34, 0)
|
||||
|
||||
user: User = await UserService(self._session).get_by_id(user_id)
|
||||
position = user.position.name if user.position else ""
|
||||
user_info = Paragraph(
|
||||
f"{user.first_name} {user.second_name}\n{position}",
|
||||
self.small_style
|
||||
)
|
||||
|
||||
doc.build([user_info], on_first_page)
|
||||
|
||||
buffer.seek(0)
|
||||
return buffer
|
||||
Reference in New Issue
Block a user