feat: create validated ZUGFeRD invoices in one console command
This commit is contained in:
1 parent
e0c15fc7f2
commit
a643cf5227
30 files changed
+1509
-207
No files matched your search
+13
-3
@@ -1,10 +1,11 @@
|
||||
from __future__ import annotations
|
||||
from pathlib import Path
|
||||
import shutil
|
||||
from .paths import presets_root
|
||||
from datetime import date, timedelta
|
||||
|
||||
from .presets import load_yaml, deep_merge, load_customer_preset
|
||||
from .invoice_number import suggest_next_invoice_number
|
||||
from .invoice_number import suggest_next_invoice_number, invoice_root_lock
|
||||
from .folder_naming import default_invoice_folder_name
|
||||
|
||||
import yaml
|
||||
@@ -24,6 +25,8 @@ def init_invoice_folder(
|
||||
project: str | None = None,
|
||||
) -> Path:
|
||||
target_dir = target_dir.resolve()
|
||||
if (target_dir / "invoice.yaml").exists() and not force:
|
||||
raise FileExistsError(f"{target_dir / 'invoice.yaml'} already exists")
|
||||
target_dir.mkdir(parents=True, exist_ok=True)
|
||||
|
||||
# Create standard subfolders
|
||||
@@ -44,6 +47,8 @@ def init_invoice_folder(
|
||||
|
||||
# Apply seller defaults
|
||||
seller_defaults = load_yaml(repo_root / "presets" / "seller.default.yaml")
|
||||
local = presets_root(repo_root)
|
||||
seller_defaults = deep_merge(seller_defaults, load_yaml(local / "seller.default.yaml"))
|
||||
merged = deep_merge(base_tpl, seller_defaults)
|
||||
|
||||
# Apply customer preset
|
||||
@@ -53,7 +58,7 @@ def init_invoice_folder(
|
||||
merged = deep_merge(merged, preset)
|
||||
logger.info("Applied customer preset: %s", customer)
|
||||
else:
|
||||
logger.warning("Customer preset not found for: %s (continuing with generic buyer)", customer)
|
||||
raise ValueError(f"Unknown customer preset: {customer}")
|
||||
|
||||
# Smart defaults for meta/payment
|
||||
today = date.today()
|
||||
@@ -102,7 +107,7 @@ def init_invoice_folder(
|
||||
logger.info("Initialized invoice folder: %s", target_dir)
|
||||
return target_dir
|
||||
|
||||
def init_invoice_under_root(
|
||||
def _init_invoice_under_root(
|
||||
invoices_root: Path,
|
||||
repo_root: Path,
|
||||
logger,
|
||||
@@ -135,3 +140,8 @@ def init_invoice_under_root(
|
||||
invoices_root=invoices_root,
|
||||
project=project,
|
||||
)
|
||||
|
||||
|
||||
def init_invoice_under_root(invoices_root: Path, **kwargs) -> Path:
|
||||
with invoice_root_lock(invoices_root):
|
||||
return _init_invoice_under_root(invoices_root, **kwargs)
|
||||
Reference in new issue
Block a user