Track configuration version and page lifecycle in wiki export.
Record created/edited/deleted-in versions per page; add History.md and update workflow docs.
This commit is contained in:
+88
-62
@@ -12,8 +12,9 @@ if str(TOOL_ROOT) not in sys.path:
|
||||
sys.path.insert(0, str(TOOL_ROOT))
|
||||
|
||||
from export1c_help import __status__, __version__ # noqa: E402
|
||||
from export1c_help.config_version import read_config_version # noqa: E402
|
||||
from export1c_help.export import export_help # noqa: E402
|
||||
from export1c_help.wiki import WikiPushError, push_wiki # noqa: E402
|
||||
from export1c_help.wiki import WikiPushError, prepare_wiki_clone, push_wiki # noqa: E402
|
||||
|
||||
|
||||
def build_parser() -> argparse.ArgumentParser:
|
||||
@@ -29,44 +30,11 @@ def build_parser() -> argparse.ArgumentParser:
|
||||
sub = p.add_subparsers(dest="cmd", required=True)
|
||||
|
||||
c = sub.add_parser("convert", help="Конвертация Help → Markdown в каталог")
|
||||
c.add_argument(
|
||||
"-s",
|
||||
"--src",
|
||||
type=Path,
|
||||
required=True,
|
||||
help="Каталог src выгрузки конфигурации (…/crm3-26/src)",
|
||||
)
|
||||
c.add_argument(
|
||||
"-o",
|
||||
"--out",
|
||||
type=Path,
|
||||
required=True,
|
||||
help="Каталог результата (wiki working tree)",
|
||||
)
|
||||
c.add_argument(
|
||||
"--objects-only",
|
||||
action="store_true",
|
||||
help="Только справка объектов (без Forms/*/Ext/Help)",
|
||||
)
|
||||
c.add_argument(
|
||||
"--keep-empty",
|
||||
action="store_true",
|
||||
help="Не пропускать почти пустые страницы",
|
||||
)
|
||||
c.add_argument(
|
||||
"--clean",
|
||||
action="store_true",
|
||||
help="Очистить --out перед записью (кроме .git)",
|
||||
)
|
||||
c.add_argument(
|
||||
"--source-label",
|
||||
default=None,
|
||||
help="Подпись источника в Home.md",
|
||||
)
|
||||
_add_convert_args(c)
|
||||
c.set_defaults(func=cmd_convert)
|
||||
|
||||
w = sub.add_parser("push", help="convert + push в Gitea wiki (.wiki.git)")
|
||||
w.add_argument("-s", "--src", type=Path, required=True)
|
||||
_add_convert_args(w, require_out=False)
|
||||
w.add_argument(
|
||||
"--wiki-url",
|
||||
required=True,
|
||||
@@ -76,7 +44,7 @@ def build_parser() -> argparse.ArgumentParser:
|
||||
"--work-dir",
|
||||
type=Path,
|
||||
default=None,
|
||||
help="Локальный clone wiki (по умолчанию: <out>/.wiki_clone)",
|
||||
help="Локальный clone wiki (по умолчанию: <out-parent>/wiki_clone)",
|
||||
)
|
||||
w.add_argument(
|
||||
"-o",
|
||||
@@ -85,30 +53,75 @@ def build_parser() -> argparse.ArgumentParser:
|
||||
default=None,
|
||||
help="Промежуточный каталог MD (по умолчанию: ./out/wiki-md)",
|
||||
)
|
||||
w.add_argument("--objects-only", action="store_true")
|
||||
w.add_argument("--keep-empty", action="store_true")
|
||||
w.add_argument(
|
||||
"--keep-unmanaged",
|
||||
action="store_true",
|
||||
help="Не удалять чужие .md в wiki перед копированием",
|
||||
)
|
||||
w.add_argument(
|
||||
"-m",
|
||||
"--message",
|
||||
default=None,
|
||||
help="Сообщение коммита wiki",
|
||||
)
|
||||
w.add_argument("-m", "--message", default=None, help="Сообщение коммита wiki")
|
||||
w.add_argument("--branch", default="main")
|
||||
w.add_argument(
|
||||
"--dry-run",
|
||||
action="store_true",
|
||||
help="Только convert, без git push",
|
||||
)
|
||||
w.add_argument("--dry-run", action="store_true", help="Только convert, без git push")
|
||||
w.set_defaults(func=cmd_push)
|
||||
|
||||
return p
|
||||
|
||||
|
||||
def _add_convert_args(p: argparse.ArgumentParser, *, require_out: bool = True) -> None:
|
||||
p.add_argument(
|
||||
"-s",
|
||||
"--src",
|
||||
type=Path,
|
||||
required=True,
|
||||
help="Каталог src выгрузки конфигурации (…/crm3-26/src)",
|
||||
)
|
||||
if require_out:
|
||||
p.add_argument(
|
||||
"-o",
|
||||
"--out",
|
||||
type=Path,
|
||||
required=True,
|
||||
help="Каталог результата (wiki working tree)",
|
||||
)
|
||||
p.add_argument(
|
||||
"--objects-only",
|
||||
action="store_true",
|
||||
help="Только справка объектов (без Forms/*/Ext/Help)",
|
||||
)
|
||||
p.add_argument(
|
||||
"--keep-empty",
|
||||
action="store_true",
|
||||
help="Не пропускать почти пустые страницы",
|
||||
)
|
||||
p.add_argument(
|
||||
"--clean",
|
||||
action="store_true",
|
||||
help="Очистить --out перед записью (кроме .git)",
|
||||
)
|
||||
p.add_argument("--source-label", default=None, help="Подпись источника в Home.md")
|
||||
p.add_argument(
|
||||
"--prev-manifest",
|
||||
type=Path,
|
||||
default=None,
|
||||
help="Предыдущий manifest.json (жизненный цикл страниц)",
|
||||
)
|
||||
p.add_argument(
|
||||
"--config-version",
|
||||
default=None,
|
||||
help="Версия конфигурации (иначе VERSION / Configuration.xml)",
|
||||
)
|
||||
|
||||
|
||||
def _print_stats(stats, dest: Path) -> None:
|
||||
print(
|
||||
f"OK: config={stats.config_version} "
|
||||
f"written={stats.pages_written} "
|
||||
f"+{stats.created_count}/~{stats.edited_count}/={stats.unchanged_count}/−{stats.deleted_count} "
|
||||
f"skipped_empty={stats.pages_skipped_empty} "
|
||||
f"total={stats.pages_total} "
|
||||
f"images={stats.images_copied} → {dest}"
|
||||
)
|
||||
|
||||
|
||||
def cmd_convert(args: argparse.Namespace) -> int:
|
||||
stats = export_help(
|
||||
args.src,
|
||||
@@ -117,38 +130,50 @@ def cmd_convert(args: argparse.Namespace) -> int:
|
||||
skip_empty=not args.keep_empty,
|
||||
clean=args.clean,
|
||||
source_label=args.source_label,
|
||||
prev_manifest_path=args.prev_manifest,
|
||||
config_version=args.config_version,
|
||||
)
|
||||
print(
|
||||
f"OK: written={stats.pages_written} "
|
||||
f"skipped_empty={stats.pages_skipped_empty} "
|
||||
f"total={stats.pages_total} "
|
||||
f"images={stats.images_copied} → {args.out}"
|
||||
)
|
||||
_print_stats(stats, args.out)
|
||||
return 0
|
||||
|
||||
|
||||
def cmd_push(args: argparse.Namespace) -> int:
|
||||
out = args.out or (TOOL_ROOT / "out" / "wiki-md")
|
||||
work = args.work_dir or (out.parent / "wiki_clone")
|
||||
branch = args.branch
|
||||
|
||||
try:
|
||||
prepare_wiki_clone(args.wiki_url, work, branch=branch)
|
||||
except WikiPushError as exc:
|
||||
print(f"wiki prepare failed:\n{exc}", file=sys.stderr)
|
||||
return 1
|
||||
|
||||
prev = args.prev_manifest or (work / "manifest.json")
|
||||
cfg = args.config_version or read_config_version(args.src)
|
||||
|
||||
stats = export_help(
|
||||
args.src,
|
||||
out,
|
||||
include_forms=not args.objects_only,
|
||||
skip_empty=not args.keep_empty,
|
||||
clean=True,
|
||||
source_label=str(args.src),
|
||||
source_label=args.source_label or str(args.src),
|
||||
prev_manifest_path=prev if prev.is_file() else None,
|
||||
config_version=cfg,
|
||||
)
|
||||
print(
|
||||
f"convert: written={stats.pages_written} "
|
||||
f"skipped_empty={stats.pages_skipped_empty} "
|
||||
f"total={stats.pages_total} → {out}"
|
||||
f"convert: config={stats.config_version} "
|
||||
f"written={stats.pages_written} "
|
||||
f"+{stats.created_count}/~{stats.edited_count}/={stats.unchanged_count}/−{stats.deleted_count} "
|
||||
f"→ {out}"
|
||||
)
|
||||
if args.dry_run:
|
||||
print("dry-run: push skipped")
|
||||
return 0
|
||||
|
||||
message = args.message or (
|
||||
f"export_1c_help v{__version__}: sync help ({stats.pages_written} pages)"
|
||||
f"export_1c_help v{__version__}: sync help cfg {stats.config_version} "
|
||||
f"({stats.pages_written} pages, +{stats.created_count}/~{stats.edited_count}/−{stats.deleted_count})"
|
||||
)
|
||||
try:
|
||||
push_wiki(
|
||||
@@ -156,8 +181,9 @@ def cmd_push(args: argparse.Namespace) -> int:
|
||||
args.wiki_url,
|
||||
work_dir=work,
|
||||
message=message,
|
||||
branch=args.branch,
|
||||
branch=branch,
|
||||
keep_unmanaged=args.keep_unmanaged,
|
||||
already_prepared=True,
|
||||
)
|
||||
except WikiPushError as exc:
|
||||
print(f"push failed:\n{exc}", file=sys.stderr)
|
||||
|
||||
Reference in New Issue
Block a user