Tutorial: Custom Prompts

On this page

RAGSystem supports three ways to control the prompt sent to your LLM, tried in this priority order (see RAGSystem._resolve_prompt):

  1. A custom prompt passed at construction time (or via set_prompt()).
  2. The built-in PromptRouter (language + question-type aware) — the default when no custom prompt is given.
  3. A hard-coded fallback template — used only if you explicitly disable prompt routing and don't supply a custom prompt.

Option 1 — A template object with .format()

Any object exposing a .format(context=..., question=...) method works. This matches the shape of a typical PromptTemplate class from a prompt-templating library.

Python · 21 lines
from dataclasses import dataclass

@dataclass
class PromptTemplate:
    template: str
    def format(self, context, question):
        return self.template.format(context=context, question=question)

tpl = PromptTemplate(
    template=(
        "You are a helpful support agent.\n\n"
        "Context:\n{context}\n\n"
        "Customer question: {question}\n"
        "Your answer:"
    )
)

rag = RAGSystem(
    vector_db=vector_db, llm=llm, chunker=chunker,
    context_manager=context_manager, prompt=tpl,
)

If your template names the parameter query instead of question, that's handled automatically — _resolve_prompt retries with query= if the first call raises KeyError/TypeError.

Option 2 — A plain callable

Python · 7 lines
def my_prompt_fn(context: str, query: str) -> str:
    return f"Given:\n{context}\n\nAnswer this in one sentence: {query}"

rag = RAGSystem(
    vector_db=vector_db, llm=llm, chunker=chunker,
    context_manager=context_manager, prompt=my_prompt_fn,
)

Option 3 — A raw format string

Python · 5 lines
rag = RAGSystem(
    vector_db=vector_db, llm=llm, chunker=chunker,
    context_manager=context_manager,
    prompt="Context: {context}\n\nQuestion: {question}\nAnswer:",
)

Swapping prompts after construction

Python · 3 lines
rag.set_prompt(tpl)          # switch to a custom template
# ... later ...
rag.set_prompt(None)         # restore PromptRouter (if enable_prompt_routing=True)

Using PromptRouter directly (outside RAGSystem)

If you're building a custom pipeline and just want the language/type-aware prompt building without the rest of RAGSystem:

Python · 6 lines
from zerda.rag.core import PromptRouter

router = PromptRouter(include_few_shot=True)
lang = router.detect_language(query)
qtype = router.detect_question_type(query, lang)
prompt = router.build(query=query, context=context, language=lang, question_type=qtype)

See PromptRouter API reference for the full list of detected question types and their trigger keywords.

Disabling prompt routing entirely

Python · 7 lines
from zerda.rag.core import RAGConfig

rag = RAGSystem(
    vector_db=vector_db, llm=llm, chunker=chunker,
    context_manager=context_manager,
    config=RAGConfig(enable_prompt_routing=False),
)

With no custom prompt and routing disabled, RAGSystem falls back to its own hard-coded bilingual instruction template (see RAGSystem._build_prompt).

Related pages