Skip to main content

S.T.A.R.K - Speech and Text Algorithmic Recognition Kit. Modern framework for creating powerfull voice assistants.

Project description

S.T.A.R.K.

Speech and Text Algorithmic Recognition Kit: a modern, async Python framework for building voice assistants and natural language interfaces. Think FastAPI, but for speech instead of HTTP.

No need to build alone. See Get Involved below.

Hello, Stark!

import anyio
from stark import run, CommandsManager, Response
from stark.interfaces.vosk import VoskSpeechRecognizer
from stark.interfaces.silero import SileroSpeechSynthesizer

VOSK_MODEL_URL = '...'    # pick one: https://alphacephei.com/vosk/models
SILERO_MODEL_URL = '...'  # pick one: https://github.com/snakers4/silero-models

manager = CommandsManager()

@manager.new('hello')                                                       # 1
def hello_command() -> Response:
    return Response('Hello, Stark!')

async def main():
    recognizer = VoskSpeechRecognizer(model_url=VOSK_MODEL_URL)             # 2
    synthesizer = SileroSpeechSynthesizer(model_url=SILERO_MODEL_URL)
    await run(manager, recognizer, synthesizer)                            # 3

if __name__ == '__main__':
    anyio.run(main)
  1. Register a command with @manager.new(...). The string is the pattern STARK matches against what the user says.
  2. Pick a speech recognizer and synthesizer. STARK ships ready-to-use ones (offline Vosk + Silero here); see Default Speech Interfaces.
  3. run() wires everything together and starts listening. This is the whole assistant.

That's a complete, working voice assistant: no cloud, no API keys. Want text-only, no microphone needed? See How to Run.

Patterns parse parameters too

@manager.new('hello $name:Word')
def hello(name: str) -> Response:
    return Response(f'Hello, {name}!')

# "hello Mark" -> "Hello, Mark!"
# "hello Archie" -> "Hello, Archie!"

Patterns aren't fixed phrases. $name:Word extracts a parameter and hands it straight to your function, typed and ready to use. See Patterns.

One sentence, multiple commands

# user says: "turn off the light and play some music"

@manager.new('turn off the light')
def lights_off() -> Response:
    return Response('Lights off.')

@manager.new('play (some|the) music')
def play_music() -> Response:
    return Response('Playing music.')

# both commands fire from that single sentence, no extra wiring required

STARK's pattern matcher parses multiple commands out of one utterance on its own, even across two separate phrases stitched together. Most voice assistants still can't do that.

Background commands

import anyio
from stark.core import AsyncResponseHandler

timer_cancelled = False

@manager.new('start timer')
async def start_timer(handler: AsyncResponseHandler) -> Response:
    global timer_cancelled
    timer_cancelled = False
    await handler.respond(Response('Timer started.', commands=[stop_timer]))  # 1
    for percent in (25, 50, 75, 100):
        await anyio.sleep(15)                                                       # 2
        if timer_cancelled:
            return Response('Timer stopped.')                                  # 3
        await handler.respond(Response(f'Timer {percent}% done.'))
    return Response('Timer finished!')

@manager.new('stop timer', hidden=True)
async def stop_timer(handler: AsyncResponseHandler) -> Response:
    global timer_cancelled
    timer_cancelled = True
    handler.pop_context()
    return Response('Stopping timer...')
  1. Responds immediately and offers a stop timer command, scoped to this context only. It won't show up anywhere else.
  2. Keeps running in the background: four checkpoints, 15 seconds apart, a minute total. The assistant is free to handle other input the whole time.
  3. A plain global flag is enough to cancel it, no extra machinery needed. (If your command needs local state instead of a shared flag, define stop_timer inside start_timer so it closes over the same variables.)

This pattern, immediate response, async progress updates, an optional cancel command, is what powers timers, downloads, or any long-running task. See Sync vs Async Commands and Commands Context.

Why STARK

  • 4 required dependencies: pydantic, asyncer, anyio, numpy. Everything else (STT/TTS backends, NLP) is opt-in. See Installation.
  • No AI required: pattern, phonetic, and fuzzy matching are deterministic and fast. LLM integration is opt-in, not a dependency. See Fallback Command / LLM Integration and where this is headed in AI Agent Platform.
  • Multilingual by design: including commands that mix languages mid-sentence.
  • Phonetic and fuzzy matching: misspellings, accents, and cross-language name lookup, handled out of the box. See Tools.
  • Nested contexts: multi-level menus, follow-ups, and stateful conversations. See Commands Context.
  • Background commands & multiple responses: fire a task, keep listening, get notified as it progresses. See Sync vs Async Commands.
  • Assistant modes: active, waiting, inactive, sleeping (wake-word), explicit, and external-trigger modes. See Running Your Assistant.
  • Modular by design: swap commands, processors, type parsers, or the entire IO layer (voice, text, a Telegram bot, your own). See How to Run.
  • 100% on-device: runs fully offline, your data stays yours.

Powered by STARK

Archie, the voice assistant built for MajorDom, runs on STARK: nested contexts for device control, multilingual input, fully offline.

Quick start

pip install stark-engine

Full docs, including installation options and extras, at stark.markparker.me.

Community

  • 💬 Discussions: questions, feedback, showcase what you built. We need all the feedback we can get to make STARK better, so don't be afraid to be first, every thread starts empty.
  • 📦 STARK-PLACE: community commands and reference implementations
  • 🐛 Issues: found a bug?

License

The S.T.A.R.K. project is licensed under the CC BY-NC-SA 4.0 International license. You're welcome to modify, contribute to the repository, create, and share forks. Just remember to attribute the original repository and its creator, abstain from commercial use, and retain the existing license.

Want to use STARK commercially, or talk about a partnership? Joint projects, hardware, contract development, anything related. Reach out via parker-industries.org/partnership. We're genuinely open to it.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

stark_engine-4.5.3.tar.gz (70.7 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

stark_engine-4.5.3-py3-none-any.whl (92.9 kB view details)

Uploaded Python 3

File details

Details for the file stark_engine-4.5.3.tar.gz.

File metadata

  • Download URL: stark_engine-4.5.3.tar.gz
  • Upload date:
  • Size: 70.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for stark_engine-4.5.3.tar.gz
Algorithm Hash digest
SHA256 f5617a5a08fba0e97ef31d63d0e791d95f7882ad72c83822aebd71eebe572dae
MD5 5db0f8f5c0759292f85ef72b7d2f9837
BLAKE2b-256 fe0a1ef8da8921d63f4f4c97b046ed4eca3150532cfe849acbc1bb3e65a5edce

See more details on using hashes here.

File details

Details for the file stark_engine-4.5.3-py3-none-any.whl.

File metadata

  • Download URL: stark_engine-4.5.3-py3-none-any.whl
  • Upload date:
  • Size: 92.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for stark_engine-4.5.3-py3-none-any.whl
Algorithm Hash digest
SHA256 f2691640aa8ab1ac34e964e2d559937bb3c65ba1d9816fb0df13aae92cd62547
MD5 35f9aa0cc41f4f372af2199c85129178
BLAKE2b-256 18ed62c08df540abcc4cfa436d6ed5f65b949f2be94a240360ccc95bd9270f50

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page