feat(mera/pdf): дисклеймер 135-ФЗ в подвале каждой страницы отчёта (блок 4.2) #2885
1 changed files with 48 additions and 6 deletions
|
|
@ -238,6 +238,11 @@ _FS_MD = "10.5pt" # базовый текст (body), значения в та
|
|||
_FS_LG = "13pt" # заголовки страниц (h2, PT Serif)
|
||||
_FS_XL = "16pt" # главный заголовок cover (h1, PT Serif)
|
||||
_FS_XXL = "22pt" # крупные ценовые цифры (dual-price блок)
|
||||
# Намеренное исключение из 6-шаговой шкалы: running-footer — @page margin-box с
|
||||
# фиксированной высотой (19mm ≈ 53.9pt), делить с mono-мета-строкой/wordmark
|
||||
# практически нечем (см. _page_footer). 135-ФЗ дисклеймер (Блок 4.2) должен
|
||||
# влезать в ~380-450 симв. на каждой странице без пятой пустой страницы.
|
||||
_FS_XXS = "5pt" # ТОЛЬКО 135-ФЗ футер-дисклеймер (_page_footer) — не переиспользовать
|
||||
|
||||
|
||||
# ── Embedded fonts (PT Sans / PT Serif, ParaType, SIL OFL 1.1) ──────────────
|
||||
|
|
@ -528,6 +533,20 @@ def _page_header(brand, report_num: str, report_date: dt.date) -> str: # type:
|
|||
)
|
||||
|
||||
|
||||
# Блок 4.2 юр-требований: должен печататься в подвале КАЖДОЙ страницы отчёта
|
||||
# (не только cover). Текст утверждён владельцем продукта дословно — не менять
|
||||
# формулировку без явного запроса. Заведён как модульная константа (не inline
|
||||
# в _page_footer), чтобы не расползалась по нескольким билдерам страниц.
|
||||
_PDF_135FZ_FOOTER_NOTICE = (
|
||||
"Документ содержит индикативный (ориентировочный) расчёт стоимости объекта, "
|
||||
"сформированный автоматически сервисом «МЕРА». Не является отчётом об оценке "
|
||||
"по Федеральному закону № 135-ФЗ и не имеет установленной этим законом "
|
||||
"юридической силы. Не предназначен для использования при ипотечном "
|
||||
"кредитовании, в судебных разбирательствах, нотариальных действиях и иных "
|
||||
"случаях, где законом предусмотрено обязательное проведение независимой оценки."
|
||||
)
|
||||
|
||||
|
||||
def _page_footer(
|
||||
brand, # type: ignore[no-untyped-def]
|
||||
report_num: str,
|
||||
|
|
@ -542,7 +561,10 @@ def _page_footer(
|
|||
|
||||
строка 1 — mono meta (№ отчёта / дата / срок действия); тонкая градиентная
|
||||
линия-разделитель; строка 2 — точка акцента + wordmark (brand.name — НЕ
|
||||
хардкод «МЕРА», white-label остаётся рабочим). Номер версии продукта здесь
|
||||
хардкод «МЕРА», white-label остаётся рабочим); строка 3 — 135-ФЗ дисклеймер
|
||||
(Блок 4.2, _PDF_135FZ_FOOTER_NOTICE) — печатается на КАЖДОЙ странице, т.к.
|
||||
footer рендерится один раз как running @page margin-box (см. вызов в
|
||||
generate_trade_in_pdf), а не per-page. Номер версии продукта здесь
|
||||
НЕ дублируется — единственное место вывода версии в PDF — running-header
|
||||
(_page_header → product_version_line()); раньше рядом с wordmark висел
|
||||
decorative "vN.N.N" (_REPORT_ENGINE_VERSION), не связанный с реальной
|
||||
|
|
@ -552,6 +574,17 @@ def _page_footer(
|
|||
на офер-странице), которого нет в веб-референсе (там нет пагинации). Не
|
||||
удалён — вынесен приглушённой строкой НАД HUD-баром, чтобы не терять
|
||||
полезную для печатного многостраничного отчёта информацию.
|
||||
|
||||
#footer-height-budget (2026-08-14, Блок 4.2): @bottom-center margin-box
|
||||
высотой = page margin-bottom (см. _build_css). Добавление 135-ФЗ текста
|
||||
(~440 симв.) потребовало И сжать существующий HUD-хром (margin-top
|
||||
6→4pt, padding-top 8→6pt, line-height мета/wordmark строк 1.35→1.15,
|
||||
градиент-разделитель margin 6pt 0→3pt 0 — экономия ~13pt), И минимально
|
||||
поднять @page margin-bottom (19mm→21mm, +2mm/+5.67pt) — сжатия одного
|
||||
подвала было недостаточно без деградации до нечитаемого. Риск: margin-bottom
|
||||
режет тело КАЖДОЙ из 4 страниц → потенциальный откат к 5-й почти пустой
|
||||
странице (регрессия, чинившаяся в 42a50cf8) — реальным рендером
|
||||
(WeasyPrint/Pango, недоступен на Windows-деве) не подтверждено, см. PR.
|
||||
"""
|
||||
note_html = ""
|
||||
if page_note:
|
||||
|
|
@ -583,18 +616,18 @@ def _page_footer(
|
|||
# тела страницы) и был источником сложности; заменён на простую тонкую
|
||||
# градиентную линию-разделитель между строками meta/wordmark.
|
||||
return f"""
|
||||
<div style="margin-top:6pt;">
|
||||
<div style="margin-top:4pt;">
|
||||
{note_html}
|
||||
<div style="border-top:1pt solid {_LINE_SOFT};padding-top:8pt;
|
||||
<div style="border-top:1pt solid {_LINE_SOFT};padding-top:6pt;
|
||||
font-family:{mono_family};font-size:{_FS_XS};letter-spacing:0.06em;
|
||||
color:{_MUTED_2};">
|
||||
color:{_MUTED_2};line-height:1.15;">
|
||||
<div style="white-space:nowrap;overflow:hidden;">
|
||||
ОТЧЁТ <span style="color:{_MUTED};">{_html.escape(report_num)}</span>
|
||||
<span style="margin-left:16pt;">ДАТА
|
||||
<span style="color:{_MUTED};">{report_date.strftime("%d.%m.%Y")}</span></span>
|
||||
{valid_until_html}
|
||||
</div>
|
||||
<div style="height:1pt;margin:6pt 0;background:linear-gradient(90deg,
|
||||
<div style="height:1pt;margin:3pt 0;background:linear-gradient(90deg,
|
||||
transparent,{_LINE_DOTTED} 15%,{_ACCENT} 50%,{_LINE_DOTTED} 85%,
|
||||
transparent);"></div>
|
||||
<div style="display:flex;align-items:center;gap:7pt;min-width:0;">
|
||||
|
|
@ -606,6 +639,11 @@ def _page_footer(
|
|||
{_html.escape(brand.name).upper()}</span>
|
||||
</div>
|
||||
</div>
|
||||
<div style="margin-top:3pt;font-family:'PT Sans','DejaVu Sans',sans-serif;
|
||||
font-size:{_FS_XXS};line-height:1.15;color:{_MUTED_2};
|
||||
overflow-wrap:anywhere;">
|
||||
{_html.escape(_PDF_135FZ_FOOTER_NOTICE)}
|
||||
</div>
|
||||
</div>
|
||||
"""
|
||||
|
||||
|
|
@ -1962,7 +2000,11 @@ def _build_css(brand=None) -> str: # type: ignore[no-untyped-def]
|
|||
}}
|
||||
@page {{
|
||||
size: A4;
|
||||
margin: 25mm 18mm 19mm 18mm;
|
||||
/* bottom 19mm→21mm (#footer-height-budget, Блок 4.2): +2mm — минимум,
|
||||
которого не хватило внутри @bottom-center margin-box (высота margin-box
|
||||
= margin-bottom) даже после сжатия HUD-хрома _page_footer под 135-ФЗ
|
||||
дисклеймер на каждой странице. См. арифметику в _page_footer(). */
|
||||
margin: 25mm 18mm 21mm 18mm;
|
||||
@top-center {{ content: element(runningHeader); vertical-align: bottom; }}
|
||||
@bottom-center {{ content: element(runningFooter); vertical-align: top; }}
|
||||
}}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue