docs: карта и руководство по структуре DWH #5

Merged
ddmitry merged 3 commits from 2-dwh-map into main 2026-09-20 20:24:01 +03:00
6 changed files with 42 additions and 16 deletions
Showing only changes of commit ec9dd4c1a8 - Show all commits

No files matched your search

+5 -3
View File
@@ -148,7 +148,7 @@
<header>
<h1 id="page-title"></h1>
<p class="lead" id="lead"></p>
<p class="navigation"><a href="db_schema.md">Руководство: от бронирования до витрины</a> · Учебная ветка main</p>
<p class="navigation"><a href="https://git.dementev.space/ddmitry/airflow-greenplum/src/docs/design/db_schema.md" target="_blank" rel="noopener noreferrer">Руководство: от бронирования до витрины (Gitea)</a> · Учебная ветка main</p>
</header>
<div class="controls">
<div class="switcher" id="switcher" aria-label="Вид связей"></div>
@@ -196,11 +196,12 @@
</div>
<aside id="details" aria-live="polite" aria-label="Карточка выбранного объекта"></aside>
</main>
<noscript>Для интерактивной карты включите JavaScript. Объяснение модели доступно в <a href="db_schema.md">руководстве</a>.</noscript>
<noscript>Для интерактивной карты включите JavaScript. Объяснение модели доступно в <a href="https://git.dementev.space/ddmitry/airflow-greenplum/src/docs/design/db_schema.md">руководстве в Gitea</a>.</noscript>
<script>
const MAP = {
"title": "Хранилище авиаперевозок",
"lead": "От бронирования до витрины: выберите таблицу или связь.",
"repository_url": "https://git.dementev.space/ddmitry/airflow-greenplum/src/",
"layers": [
{
"id": "source",
@@ -5001,7 +5002,8 @@
links.forEach((item) => {
const row = document.createElement("li");
const link = document.createElement("a");
link.href = item.url;
// Выбор таблицы остается в локальной карте; файлы открываются в Gitea.
link.href = item.url.startsWith("#") ? item.url : new URL(item.url, new URL("docs/design/", MAP.repository_url)).href;
link.target = "_blank";
link.rel = "noopener noreferrer";
link.textContent = item.label;
+12 -3
View File
@@ -1,8 +1,8 @@
# Исходники карты DWH
Готовый файл - [../architecture-map.html](../architecture-map.html).
Откройте его локально в браузере. Сервер и интернет не требуются;
SQL и Markdown открываются из соседних каталогов репозитория.
Откройте его локально в браузере. Для самой карты сервер и интернет не требуются.
Ссылки на SQL, DAG и Markdown открывают Gitea, поэтому для переходов нужен интернет.
Учебный маршрут находится в [руководстве о структуре](../db_schema.md).
## Редактирование и сборка
@@ -28,6 +28,13 @@ uv run docs/design/architecture-map/render.py --check
Проверка входов учитывает именованные таблицы в FROM/JOIN;
смысл соединений нужно сверять при изменении SQL вручную.
`repository_url` в `map.json` задает адрес Gitea с окончанием `/src/`.
В нем нет имени ветки или коммита: Gitea открывает файл из текущей ветки
по умолчанию. Пути в `links` остаются относительными к готовому HTML,
чтобы сборка проверяла файлы и разделы в локальном репозитории;
интерфейс преобразует их в адреса Gitea. Ссылки вида `#node=…` остаются
в локальной карте. Ссылка на руководство в шапке собирается из того же адреса.
Внешние `stg.*_ext` представлены в карточках STG, поскольку это входы чтения,
а не еще одна копия данных. Поля источника сверяются с контрактом PXF.
Для заглушек используются DDL и `docs/assignment/analyst_spec.md`.
@@ -55,6 +62,8 @@ uv run docs/design/architecture-map/render.py --check
4. У факта откройте обе роли `dim_airports`, путь через `ods.routes`
и выбор версии `dim_routes`. Проверьте отдельные карточки связей.
5. Откройте адрес объекта, обновите страницу, проверьте назад/вперед.
Откройте DDL, загрузку, DQ и пункт задания из карточки.
Откройте DDL, загрузку, DQ, DAG и пункт задания из карточки в Gitea.
Проверьте форматирование Markdown, подсветку кода и переход к разделу задания.
Ссылка на таблицу должна открывать локальную карту с тем же выбором.
6. Проверьте выбор клавишами Enter/пробел и вид на узком экране.
На узком экране карта прокручивается, карточка находится под ней.
+1
View File
@@ -1,6 +1,7 @@
{
"title": "Хранилище авиаперевозок",
"lead": "От бронирования до витрины: выберите таблицу или связь.",
"repository_url": "https://git.dementev.space/ddmitry/airflow-greenplum/src/",
"layers": [
{
"id": "source",
+15 -2
View File
@@ -10,8 +10,9 @@ from __future__ import annotations
import argparse
import json
import re
from html import escape
from pathlib import Path
from urllib.parse import unquote, urlsplit
from urllib.parse import unquote, urljoin, urlsplit
HERE = Path(__file__).resolve().parent
ROOT = HERE.parents[2]
@@ -34,6 +35,15 @@ def headings(text: str) -> set[str]:
def validate(data: dict) -> None:
"""Сверить объекты, поля, статусы, входы готовых SQL и локальные ссылки."""
repository = urlsplit(data["repository_url"])
if (
repository.scheme != "https"
or not repository.netloc
or not repository.path.endswith("/src/")
or repository.query
or repository.fragment
):
raise ValueError("Укажите HTTPS-адрес репозитория Gitea с окончанием /src/")
nodes = {node["id"]: node for node in data["nodes"]}
if len(nodes) != len(data["nodes"]):
raise ValueError("Повторяется идентификатор объекта")
@@ -140,7 +150,10 @@ def main() -> int:
if template.count(MARKER) != 1:
raise ValueError("В шаблоне должен быть ровно один маркер данных")
payload = json.dumps(data, ensure_ascii=False, indent=2).replace("<", "\\u003c")
result = NOTICE + template.replace(MARKER, payload)
guide_url = urljoin(data["repository_url"], "docs/design/db_schema.md")
result = NOTICE + template.replace(MARKER, payload).replace(
"__GUIDE_URL__", escape(guide_url, quote=True)
)
if args.check:
if not OUTPUT.exists() or OUTPUT.read_text(encoding="utf-8") != result:
raise ValueError(
+4 -3
View File
@@ -147,7 +147,7 @@
<header>
<h1 id="page-title"></h1>
<p class="lead" id="lead"></p>
<p class="navigation"><a href="db_schema.md">Руководство: от бронирования до витрины</a> · Учебная ветка main</p>
<p class="navigation"><a href="__GUIDE_URL__" target="_blank" rel="noopener noreferrer">Руководство: от бронирования до витрины (Gitea)</a> · Учебная ветка main</p>
</header>
<div class="controls">
<div class="switcher" id="switcher" aria-label="Вид связей"></div>
@@ -195,7 +195,7 @@
</div>
<aside id="details" aria-live="polite" aria-label="Карточка выбранного объекта"></aside>
</main>
<noscript>Для интерактивной карты включите JavaScript. Объяснение модели доступно в <a href="db_schema.md">руководстве</a>.</noscript>
<noscript>Для интерактивной карты включите JavaScript. Объяснение модели доступно в <a href="__GUIDE_URL__">руководстве в Gitea</a>.</noscript>
<script>
const MAP = /*__MAP_DATA__*/;
const NS = "http://www.w3.org/2000/svg";
@@ -252,7 +252,8 @@
links.forEach((item) => {
const row = document.createElement("li");
const link = document.createElement("a");
link.href = item.url;
// Выбор таблицы остается в локальной карте; файлы открываются в Gitea.
link.href = item.url.startsWith("#") ? item.url : new URL(item.url, new URL("docs/design/", MAP.repository_url)).href;
link.target = "_blank";
link.rel = "noopener noreferrer";
link.textContent = item.label;
+5 -5
View File
@@ -15,11 +15,11 @@ xdg-open docs/design/architecture-map.html
```
На Windows можно открыть этот же файл в Проводнике. Сервер, интернет и работающий
Docker для карты не нужны. Храните HTML рядом с остальными файлами репозитория:
ссылки из карточек ведут в локальные SQL и Markdown.
Браузер может показать Markdown как текст, а SQL предложить скачать.
Скачанный файл можно открыть в редакторе; для форматированного чтения
руководства используйте Markdown preview.
Docker для карты не нужны: все ее данные включены в HTML.
Ссылки на SQL, DAG, задание и это руководство открывают файлы в Gitea:
документы — с форматированием, код — с подсветкой синтаксиса.
Для этих переходов нужен интернет. Файлы берутся из текущей ветки репозитория
по умолчанию.
**В Gitea ссылка на HTML обычно показывает исходный текст, а не карту.**
Сначала откройте локальный HTML. Адресная ссылка вида