DEV Community

Cover image for Building a Context-Aware, Streaming DeepSeek Chatbot in your Terminal (with R1 Reasoning support!)
Rodney Gitonga
Rodney Gitonga

Posted on

Building a Context-Aware, Streaming DeepSeek Chatbot in your Terminal (with R1 Reasoning support!)

I wanted to share a project I've been working on: a fully-featured, highly interactive DeepSeek Terminal Chatbot.

It goes beyond simple command-line inputs to implement dynamic routing (Native vs. OpenRouter), real-time markdown streaming, R1 reasoning-process visualizations, and local chat logging.

Here's how it looks:


What Makes This Chatbot Different?

Many CLI chatbots are built as quick scripts that lack robust state management, visual styling, or flexible configuration. This project solves those limitations with several key features:

  1. Dynamic Route & Key Detection The script automatically detects the type of API key you are using and configures itself accordingly:
    • OpenRouter key (sk-or-v1-...): Automatically configures the base URL to https://openrouter.ai/api/v1 and switches defaults to deepseek/deepseek-chat or deepseek/deepseek-r1.
    • DeepSeek Native key (sk-...): Configures the base URL to https://api.deepseek.com and targets deepseek-chat or deepseek-reasoner.

This lets you use the same codebase with either your direct DeepSeek account or your OpenRouter credits.

  1. DeepSeek-R1 (Thinking) Support DeepSeek's reasoning model (R1) streams reasoning tokens before outputting its final response. The script captures this stream (reasoning_content or reasoning depending on the provider) and renders it dynamically in a dim blockquote block, so you can watch the model think in real time:
 Extract reasoning tokens dynamically
reasoning_token = getattr(delta, 'reasoning_content', None) or getattr(delta, 'reasoning', None)
if reasoning_token:
    reasoning_response += reasoning_token
     Render thinking process live...
Enter fullscreen mode Exit fullscreen mode
  1. True Conversation Context A common beginner bug is only passing the last user message to the API completion call, which breaks multi-turn memory. This script maintains the session state inside a messages queue, forwarding the complete context for natural, ongoing conversation:
 Maintaining the chat session state
messages.append({"role": "user", "content": msg})
response_stream = client.chat.completions.create(
    model=current_model,
    messages=messages,  Complete session history
    stream=True
)
Enter fullscreen mode Exit fullscreen mode
  1. Premium Console UI via rich
    The interface uses the Python rich library to render:

    • Live Markdown streaming (headers, code snippets, syntax highlighting, lists, tables).
    • Spinner statuses while waiting for first tokens.
    • Beautiful system layout panels.
  2. Interactive Commands
    You can issue commands inside the chat prompt starting with /:

    • /model <name>: Switch models on the fly (e.g. swap to the reasoning model).
    • /clear: Clear the conversation history.
    • /save [filename]: Export the current session into a cleanly formatted markdown log.
    • /help and /exit: View commands or quit gracefully.

Getting Started

Install Dependencies

pip install openai rich python-dotenv
Enter fullscreen mode Exit fullscreen mode

Configure Credentials (.env)

DEEPSEEK_API_KEY=your_api_key_here
Enter fullscreen mode Exit fullscreen mode

Run the Script

python ai.py
Enter fullscreen mode Exit fullscreen mode

The Code

You can check out the repository or inspect the full script at: [Link to your GitHub repo here]

I'd love to hear your thoughts on this! How are you integrating DeepSeek models into your daily developer workflows?

Top comments (0)