Files
obsidian-api/app/property_commands.py
T

56 lines
1.7 KiB
Python
Raw Normal View History

import re
from pathlib import Path
from app.command_target import extract_command_target, parse_kv_arg
from app.vaults import vault_root_for_target
DATE_ONLY_RE = re.compile(r"^\d{4}-\d{2}-\d{2}T?$")
def arg_value(args:list[str], name:str) -> str|None:
for arg in args:
parsed = parse_kv_arg(arg)
if parsed and parsed[0] == name and parsed[1]:
return parsed[1]
return None
def normalize_property_datetime_args(args:list[str]) -> list[str]:
target = extract_command_target(args)
if target.command != "property:set" or arg_value(args, "type") != "datetime":
return args
value = arg_value(args, "value")
if not value or not DATE_ONLY_RE.match(value):
return args
normalized_value = f"{value.rstrip('T')}T00:00:00"
return [f"value={normalized_value}" if parse_kv_arg(arg) == ("value", value) else arg for arg in args]
def vault_note_path(vault_root:Path, path:str) -> Path:
note_path = (vault_root / path).resolve()
try:
note_path.relative_to(vault_root.resolve())
except ValueError as exc:
raise PermissionError(f"path escapes vault: {path}") from exc
return note_path
def create_missing_property_file(args:list[str], cwd:Path) -> None:
target = extract_command_target(args)
if target.command != "property:set":
return
path = arg_value(args, "path")
if not path:
return
note_path = vault_note_path(vault_root_for_target(target, cwd), path)
if note_path.exists():
return
note_path.parent.mkdir(parents=True, exist_ok=True)
note_path.write_text("", encoding="utf-8")
def prepare_property_args(args:list[str], cwd:Path) -> list[str]:
args = normalize_property_datetime_args(args)
create_missing_property_file(args, cwd)
return args