Python CLI and GUI clients to interact with OpenAI's API.
Note: Prefer your distribution packages if possible.
For the CLI client:
pip install openai richFor the GUI client (Tkinter is often part of the standard Python installation):
pip install openai tkinterweb mistletoe pygmentsExpects an OPENAI_API_KEY environment variable, or a .api_key file in the repo
directory or data directory (~/.chatgpt-gui/) as a fallback. The filename is in
.gitignore already.
Conversations are automatically saved as JSON files in ~/.chatgpt-gui/. Override the
location with the CHATGPT_GUI_DATA_DIR environment variable:
export CHATGPT_GUI_DATA_DIR=/path/to/your/data./cli.pyQuit with q, x, exit, quit, Ctrl+C, or Ctrl+D.
| Flag | Description |
|---|---|
-m, --multiline |
Multiline input mode — type your message, then enter SEND to submit |
-b, --batch-mode |
Non-interactive mode for pipes and redirection |
-M, --model |
Select a specific model |
-w, --web-search |
Enable web search with source extraction |
-ig, --image-generation |
Enable image generation; images saved to the data directory |
--image-size |
Generated image size (auto or WIDTHxHEIGHT, e.g. 1024x1024); default 1024x1024 |
--image-quality |
Generated image quality: auto, low, medium, high; default low |
--image-format |
Generated image format: png, jpeg, webp; default jpeg |
--image-model |
Image generation model: gpt-image-2, gpt-image-1.5, gpt-image-1, gpt-image-1-mini; default gpt-image-1-mini |
-p, --prepend |
Prepend a string (followed by two newlines) to the first message |
-pf, --prepend-file |
Prepend a file's contents to the first message |
-i, --image |
Image file(s) to include |
-f, --file |
Document(s) to include |
-vf, --vectorize-file |
Document(s) to upload to a vector store for semantic file search |
-vs, --vector-store |
Use a pre-existing vector store by ID for semantic file search; can be combined with -vf to upload additional files into it (files are kept after the session) |
-r, --rich |
Render Markdown with rich text formatting in the terminal |
-d, --debug |
Pretty-print raw API responses to stderr |
-l, --list-known |
List models with known pricing |
-L, --list-all |
List all available models |
./cli.py files list # list uploaded files
./cli.py files add report.pdf # upload a file, prints the file ID
./cli.py files delete FILE_ID ... # delete one or more files by ID
./cli.py files purge # delete all uploaded files./cli.py vectors list # list vector stores
./cli.py vectors create NAME # create an empty vector store, prints the vector store ID
./cli.py vectors create NAME doc1.pdf doc2.pdf # create a vector store, upload and index files, prints the ID
./cli.py vectors create NAME doc.pdf --no-wait # same but return immediately without waiting for indexing
./cli.py vectors delete VECTOR_STORE_ID # delete a vector store
./cli.py vectors purge # delete all vector stores
./cli.py vectors files list VECTOR_STORE_ID # list files in a vector store
./cli.py vectors files add VECTOR_STORE_ID file1.pdf ... # upload and add file(s) to a vector store
./cli.py vectors files add-id VECTOR_STORE_ID FILE_ID ... # add already-uploaded file(s) to a vector store by ID
./cli.py vectors files delete VECTOR_STORE_ID FILE_ID ... # remove one or more files from a vector store./cli.py -b <<< "Tell a joke" > joke.txt
./cli.py -b < prompt.txt > output.txt
./cli.py -b --prepend-file summarize_prompt.txt < article.txt
./cli.py -b -p "Summarize the following text:" < article.txt
./cli.py -b -f report.pdf <<< "Summarize this document"
./cli.py -b -f cv.pdf job.pdf <<< "Is this candidate a good fit?"
./cli.py -b -vf contracts/*.pdf <<< "Which contracts mention arbitration?"
./cli.py -vf docs/*.pdf # interactive Q&A session across a document collection
./cli.py -vs vs_abc123 # interactive Q&A using a pre-existing vector store
./cli.py -vs vs_abc123 -vf extra.pdf # same, but also upload extra.pdf into it (file kept after session)The tool is quite powerful with guake drop-down terminal and alias like this:
alias gpt='$HOME/projects/chatgpt-gui/cli.py'More useful example to review patch of PR for currently checked out branch in the current
directory (expects gh client installed):
alias review='gh pr diff --patch | gpt -b -pf $HOME/.pr-review'The .pr-review file contains:
Summarize and review the following patch:
./gui.pyBrowse past conversations and chat interactively with full Markdown rendering and syntax highlighting.
- Resizable panes — drag the separators between panels to adjust layout
- Sortable conversation list — click the column header to toggle sort order
- Keyboard shortcuts —
Enterto send,Shift+Enterfor a new line
whisper.py— transcribe audio using OpenAI's Whisper APIdale.py— generate images using DALL-E 3 (./dale.py "prompt" [-n N] [-j N])
Install test dependencies:
pip install pytest pytest-xdistFormat, lint, and test with:
make format
make lint
make test # sequential
make xtest # parallel (16 workers)Run a single test suite:
python -m pytest tests/e2e_test.py::TestBatchMode -vRun a single test case:
python -m pytest tests/e2e_test.py::TestBatchMode::test_batch_basic -vContributions are welcome! Please feel free to submit a pull request.
If you encounter any issues or have any questions, please open an issue on GitHub.