Building a streamlit app that can be run simply with "uvx [package-name]"

1 week ago 21
ARTICLE AD BOX

end-users simply run uvx foobarbaz

Yours would not be the first such application. But you failed to cite similar apps. We will touch on a few at the end.

You should first scale back your requirements slightly. Instead of insisting that streamlit myfile.py shall run, it would be simpler to start with requiring that python myfile.py shall run, as that is uvx's default.

(1.) structure

foobarbaz/src/foobarbaz/__init__.py

That's not my favorite filename. I'm sure you could make it work. But I have found that putting my code under src/ introduces the slightly unpleasant need to adjust an env var with env PYTHONPATH=src:. python myfile.py, and I wouldn't wish that extra speedbump upon your initial debugging efforts. Consider putting your source folder at toplevel, at least initially, so we're running foobarbaz/foobarbaz/__main__.py. Once you have a working system, then of course you can tweak it to your heart's content.

(2.) runner

You can run streamlit in "a truly cross-platform way" via import subprocess. But if you don't want to run it as a child process, then POSIX-compliant systems can use os.execve(path_to_streamlit, args, env). That would certainly work on linux, FreeBSD, MacOS and the like. I don't have a Windows system to test on. If by "cross-platform" you have NT, OS/2 or other exotic systems in mind, you'll have some debugging ahead of you.

(3.) test locally

Recall that both pip and uvx can accept a GitHub URL (with SHA1 commit!) as easily as they accept a pypi project name. So you should be able to do a bunch of git push tests and verify that each one does what you expect, prior to publishing version 0.1 on pypi. Also recall that, before a 1.0 release, SemVer imposes no back-compat constraints on you.


Other authors have tackled goals similar to your own. Let's examine some.

uvx mypy --strict ., repo at https://github.com/python/mypy, see __main__.py uvx ruff check ., repo at https://github.com/astral-sh/ruff, showing that Rust and other language environments can work for this Use Case uvx pycowsay moo, repo at https://pypi.org/project/pycowsay, very simple, still uses the ancient setup.py, hasn't been updated for recent interpreters so it displays the occcasional warning

I feel that https://github.com/cs01/pycowsay/tree/master/pycowsay is very instructive for your Use Case.

I encourage you to stick to the modern and minimal pyproject.toml approach to packaging. Avoid creating a setup.py file, as you don't need it in today's ecosystem.


Please post the GitHub URL of your foobarbaz repo here. We want to know how things turned out.

Read Entire Article