fixing...
This commit is contained in:
@@ -1,20 +1,29 @@
|
||||
# project_manager.py
|
||||
import subprocess, datetime, tomllib, tomli_w, re
|
||||
import subprocess
|
||||
import datetime
|
||||
import tomllib
|
||||
import tomli_w
|
||||
import re
|
||||
from pathlib import Path
|
||||
|
||||
TS_FMT = "%Y-%m-%dT%H:%M:%S"
|
||||
|
||||
|
||||
def now_ts() -> str:
|
||||
return datetime.datetime.now().strftime(TS_FMT)
|
||||
|
||||
def parse_ts(s: str):
|
||||
try: return datetime.datetime.strptime(s, TS_FMT)
|
||||
except: return None
|
||||
|
||||
# ── entry serialisation ───────────────────────────────────────────────────────
|
||||
def parse_ts(s: str):
|
||||
try:
|
||||
return datetime.datetime.strptime(s, TS_FMT)
|
||||
except Exception:
|
||||
return None
|
||||
|
||||
|
||||
# ── entry serialisation ──────────────────────────────────────────────────────
|
||||
|
||||
def entry_to_str(entry: dict) -> str:
|
||||
"""Serialise a disc entry dict -> stored string. Always uses real newlines."""
|
||||
"""Serialise a disc entry dict -> stored string."""
|
||||
ts = entry.get("ts", "")
|
||||
role = entry.get("role", "User")
|
||||
content = entry.get("content", "")
|
||||
@@ -22,11 +31,11 @@ def entry_to_str(entry: dict) -> str:
|
||||
return f"@{ts}\n{role}:\n{content}"
|
||||
return f"{role}:\n{content}"
|
||||
|
||||
|
||||
def str_to_entry(raw: str, roles: list[str]) -> dict:
|
||||
"""Parse a stored string back to a disc entry dict."""
|
||||
ts = ""
|
||||
rest = raw
|
||||
# Strip optional leading @timestamp line
|
||||
if rest.startswith("@"):
|
||||
nl = rest.find("\n")
|
||||
if nl != -1:
|
||||
@@ -48,29 +57,37 @@ def str_to_entry(raw: str, roles: list[str]) -> dict:
|
||||
content = parts[1].strip() if len(parts) > 1 else ""
|
||||
return {"role": matched_role, "content": content, "collapsed": False, "ts": ts}
|
||||
|
||||
# ── git helpers ───────────────────────────────────────────────────────────────
|
||||
|
||||
# ── git helpers ──────────────────────────────────────────────────────────────
|
||||
|
||||
def get_git_commit(git_dir: str) -> str:
|
||||
try:
|
||||
r = subprocess.run(["git", "rev-parse", "HEAD"],
|
||||
capture_output=True, text=True, cwd=git_dir, timeout=5)
|
||||
r = subprocess.run(
|
||||
["git", "rev-parse", "HEAD"],
|
||||
capture_output=True, text=True, cwd=git_dir, timeout=5,
|
||||
)
|
||||
return r.stdout.strip() if r.returncode == 0 else ""
|
||||
except Exception:
|
||||
return ""
|
||||
|
||||
|
||||
def get_git_log(git_dir: str, n: int = 5) -> str:
|
||||
try:
|
||||
r = subprocess.run(["git", "log", "--oneline", f"-{n}"],
|
||||
capture_output=True, text=True, cwd=git_dir, timeout=5)
|
||||
r = subprocess.run(
|
||||
["git", "log", "--oneline", f"-{n}"],
|
||||
capture_output=True, text=True, cwd=git_dir, timeout=5,
|
||||
)
|
||||
return r.stdout.strip() if r.returncode == 0 else ""
|
||||
except Exception:
|
||||
return ""
|
||||
|
||||
# ── default structures ────────────────────────────────────────────────────────
|
||||
|
||||
# ── default structures ───────────────────────────────────────────────────────
|
||||
|
||||
def default_discussion() -> dict:
|
||||
return {"git_commit": "", "last_updated": now_ts(), "history": []}
|
||||
|
||||
|
||||
def default_project(name: str = "unnamed") -> dict:
|
||||
return {
|
||||
"project": {"name": name, "git_dir": ""},
|
||||
@@ -84,16 +101,19 @@ def default_project(name: str = "unnamed") -> dict:
|
||||
},
|
||||
}
|
||||
|
||||
# ── load / save ───────────────────────────────────────────────────────────────
|
||||
|
||||
# ── load / save ──────────────────────────────────────────────────────────────
|
||||
|
||||
def load_project(path) -> dict:
|
||||
with open(path, "rb") as f:
|
||||
return tomllib.load(f)
|
||||
|
||||
|
||||
def save_project(proj: dict, path):
|
||||
with open(path, "wb") as f:
|
||||
tomli_w.dump(proj, f)
|
||||
|
||||
|
||||
# ── migration helper ─────────────────────────────────────────────────────────
|
||||
|
||||
def migrate_from_legacy_config(cfg: dict) -> dict:
|
||||
@@ -105,11 +125,12 @@ def migrate_from_legacy_config(cfg: dict) -> dict:
|
||||
proj[key] = dict(cfg[key])
|
||||
disc = cfg.get("discussion", {})
|
||||
proj["discussion"]["roles"] = disc.get("roles", ["User", "AI", "Vendor API", "System"])
|
||||
main = proj["discussion"]["discussions"]["main"]
|
||||
main["history"] = disc.get("history", [])
|
||||
main["last_updated"] = now_ts()
|
||||
main_disc = proj["discussion"]["discussions"]["main"]
|
||||
main_disc["history"] = disc.get("history", [])
|
||||
main_disc["last_updated"] = now_ts()
|
||||
return proj
|
||||
|
||||
|
||||
# ── flat config for aggregate.run() ─────────────────────────────────────────
|
||||
|
||||
def flat_config(proj: dict, disc_name: str | None = None) -> dict:
|
||||
|
||||
Reference in New Issue
Block a user