Spaces:
Running
Running
File size: 3,392 Bytes
4b1d79b | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 | """Local file browser rendered inside Streamlit, without desktop GUI calls."""
from pathlib import Path
import streamlit as st
from app_environment import hosted_mode
def close_picker():
st.session_state.picker_open = False
def set_directory(path):
target = Path(path).expanduser()
try:
if not target.is_dir():
raise ValueError('Folder not found or not accessible.')
st.session_state.picker_directory = str(target.resolve())
st.session_state.picker_address = str(target.resolve())
st.session_state.pop('picker_error', None)
except (OSError, ValueError) as e:
st.session_state.picker_error = str(e)
def navigate_address():
set_directory(st.session_state.picker_address.strip().strip('"'))
def choose_file(path):
st.session_state.pending_model = str(path.resolve())
close_picker()
def file_size(size):
return f'{size / 1024**3:.2f} GB' if size >= 1024**3 else f'{size / 1024**2:.1f} MB'
@st.dialog('Open model', width='large', on_dismiss=close_picker)
def show_model_picker():
if hosted_mode():
st.error('Server filesystem browsing is disabled in the hosted app. Use uploads or Hugging Face instead.')
return
current = Path(st.session_state.get('picker_directory', str(Path.cwd())))
if 'picker_address' not in st.session_state:
st.session_state.picker_address = str(current)
up, address = st.columns([1, 8], vertical_alignment='bottom')
up.button('↑ Up', disabled=current == current.parent, on_click=set_directory,
args=(current.parent,), use_container_width=True)
address.text_input('Folder path', key='picker_address', on_change=navigate_address,
placeholder='Paste a folder path and press Enter')
current = Path(st.session_state.get('picker_directory', str(Path.cwd())))
if 'picker_error' in st.session_state:
st.error(st.session_state.picker_error)
st.caption(f'Showing: {current}')
try:
entries = sorted(current.iterdir(), key=lambda p: p.name.lower())
folders = [p for p in entries if p.is_dir() and not p.name.startswith('.')]
files = [p for p in entries if p.is_file() and p.suffix.lower() in {'.gguf', '.safetensors'}]
except OSError as e:
st.error(f'Could not read this folder: {e}')
return
with st.container(height=300, border=True):
for folder in folders:
st.button(f'📁 {folder.name}', key=f'folder:{folder}', on_click=set_directory,
args=(folder,), use_container_width=True)
for file in files:
label, size = st.columns([5, 1], vertical_alignment='center')
if label.button(f'📄 {file.name}', key=f'file:{file}', use_container_width=True):
choose_file(file)
st.rerun()
try:
size.caption(file_size(file.stat().st_size))
except OSError:
size.caption('Unavailable')
if not files:
st.info('No GGUF or safetensors files here. Open a subfolder or enter another path above.')
count, cancel = st.columns([5, 1], vertical_alignment='center')
count.caption(f'{len(folders)} folders · {len(files)} model files · Click a model to select it')
if cancel.button('Cancel', use_container_width=True):
close_picker()
st.rerun()
|