Spaces:
Running
Running
Commit ·
dc86fd7
1
Parent(s): 5c70ff1
Case study: stabilize file browser on switch and add light preview
Browse files- streamlit-client/app.py +52 -4
streamlit-client/app.py
CHANGED
|
@@ -456,6 +456,48 @@ def load_chat_from_file(chat_path: Path) -> list[dict]:
|
|
| 456 |
return data.get("messages", [])
|
| 457 |
|
| 458 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 459 |
def get_next_memo_number(memory_dir: Path) -> int:
|
| 460 |
if not memory_dir.exists():
|
| 461 |
return 1
|
|
@@ -578,21 +620,27 @@ if st.session_state.view_mode == "case_study":
|
|
| 578 |
case_dir = selected_path.parent
|
| 579 |
ws_dir = case_dir / "workspace"
|
| 580 |
browse_path = ws_dir if ws_dir.exists() else case_dir
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 581 |
# Use a case-specific key so switching case study resets browser state correctly
|
| 582 |
fb_key = f"case_study_file_browser_{case_dir.name}"
|
| 583 |
with st.expander("📂 Workspace Files (Agent Code)", expanded=False):
|
| 584 |
-
st.caption(f"Browsing: `{
|
| 585 |
if st_file_browser is not None:
|
| 586 |
-
st_file_browser(
|
| 587 |
-
|
| 588 |
key=fb_key,
|
| 589 |
show_choose_file=True,
|
| 590 |
show_download_file=True,
|
| 591 |
show_delete_file=False,
|
| 592 |
show_new_folder=False,
|
| 593 |
show_upload_file=False,
|
| 594 |
-
show_preview=
|
| 595 |
)
|
|
|
|
| 596 |
else:
|
| 597 |
st.info("Install `streamlit-file-browser` to browse workspace files in Case Study mode.")
|
| 598 |
st.stop()
|
|
|
|
| 456 |
return data.get("messages", [])
|
| 457 |
|
| 458 |
|
| 459 |
+
def _render_case_file_preview(event: dict | None, root_path: Path):
|
| 460 |
+
"""Render a light-theme preview for selected files from streamlit-file-browser."""
|
| 461 |
+
if not event or not isinstance(event, dict):
|
| 462 |
+
return
|
| 463 |
+
if event.get("type") != "SELECT_FILE":
|
| 464 |
+
return
|
| 465 |
+
target = (event.get("target") or {}).get("path")
|
| 466 |
+
if not target:
|
| 467 |
+
return
|
| 468 |
+
file_path = (root_path / target).resolve()
|
| 469 |
+
if not file_path.exists() or file_path.is_dir():
|
| 470 |
+
st.warning(f"File `{target}` not found under current workspace.")
|
| 471 |
+
return
|
| 472 |
+
|
| 473 |
+
st.markdown("#### File Preview")
|
| 474 |
+
suffix = file_path.suffix.lower()
|
| 475 |
+
if suffix in {".png", ".jpg", ".jpeg", ".gif", ".webp"}:
|
| 476 |
+
st.image(str(file_path))
|
| 477 |
+
return
|
| 478 |
+
|
| 479 |
+
# Text/code preview (light theme via existing CSS on st.code)
|
| 480 |
+
max_chars = 300_000
|
| 481 |
+
with open(file_path, "r", encoding="utf-8", errors="ignore") as f:
|
| 482 |
+
content = f.read(max_chars + 1)
|
| 483 |
+
if len(content) > max_chars:
|
| 484 |
+
content = content[:max_chars] + "\n\n... [truncated]"
|
| 485 |
+
|
| 486 |
+
lang_map = {
|
| 487 |
+
".py": "python",
|
| 488 |
+
".js": "javascript",
|
| 489 |
+
".ts": "typescript",
|
| 490 |
+
".json": "json",
|
| 491 |
+
".md": "markdown",
|
| 492 |
+
".sh": "bash",
|
| 493 |
+
".yml": "yaml",
|
| 494 |
+
".yaml": "yaml",
|
| 495 |
+
".csv": "text",
|
| 496 |
+
".txt": "text",
|
| 497 |
+
}
|
| 498 |
+
st.code(content, language=lang_map.get(suffix, "text"))
|
| 499 |
+
|
| 500 |
+
|
| 501 |
def get_next_memo_number(memory_dir: Path) -> int:
|
| 502 |
if not memory_dir.exists():
|
| 503 |
return 1
|
|
|
|
| 620 |
case_dir = selected_path.parent
|
| 621 |
ws_dir = case_dir / "workspace"
|
| 622 |
browse_path = ws_dir if ws_dir.exists() else case_dir
|
| 623 |
+
browse_root = str(browse_path.resolve())
|
| 624 |
+
# Force one rerun when case/workspace root changes to avoid first-empty browser state.
|
| 625 |
+
if st.session_state.get("case_fb_root") != browse_root:
|
| 626 |
+
st.session_state.case_fb_root = browse_root
|
| 627 |
+
st.rerun()
|
| 628 |
# Use a case-specific key so switching case study resets browser state correctly
|
| 629 |
fb_key = f"case_study_file_browser_{case_dir.name}"
|
| 630 |
with st.expander("📂 Workspace Files (Agent Code)", expanded=False):
|
| 631 |
+
st.caption(f"Browsing: `{browse_root}`")
|
| 632 |
if st_file_browser is not None:
|
| 633 |
+
fb_event = st_file_browser(
|
| 634 |
+
browse_root,
|
| 635 |
key=fb_key,
|
| 636 |
show_choose_file=True,
|
| 637 |
show_download_file=True,
|
| 638 |
show_delete_file=False,
|
| 639 |
show_new_folder=False,
|
| 640 |
show_upload_file=False,
|
| 641 |
+
show_preview=False,
|
| 642 |
)
|
| 643 |
+
_render_case_file_preview(fb_event, browse_path.resolve())
|
| 644 |
else:
|
| 645 |
st.info("Install `streamlit-file-browser` to browse workspace files in Case Study mode.")
|
| 646 |
st.stop()
|