haiku.rag 0.5.1__py3-none-any.whl → 0.5.2__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of haiku.rag might be problematic. Click here for more details.

haiku/rag/app.py CHANGED
@@ -32,9 +32,9 @@ class HaikuRAGApp:
32
32
  f"[b]Document with id [cyan]{doc.id}[/cyan] added successfully.[/b]"
33
33
  )
34
34
 
35
- async def add_document_from_source(self, file_path: Path):
35
+ async def add_document_from_source(self, source: str):
36
36
  async with HaikuRAG(db_path=self.db_path) as self.client:
37
- doc = await self.client.create_document_from_source(file_path)
37
+ doc = await self.client.create_document_from_source(source)
38
38
  self._rich_print_document(doc, truncate=True)
39
39
  self.console.print(
40
40
  f"[b]Document with id [cyan]{doc.id}[/cyan] added successfully.[/b]"
haiku/rag/cli.py CHANGED
@@ -81,7 +81,7 @@ def add_document_text(
81
81
 
82
82
  @cli.command("add-src", help="Add a document from a file path or URL")
83
83
  def add_document_src(
84
- file_path: Path = typer.Argument(
84
+ source: str = typer.Argument(
85
85
  help="The file path or URL of the document to add",
86
86
  ),
87
87
  db: Path = typer.Option(
@@ -91,7 +91,7 @@ def add_document_src(
91
91
  ),
92
92
  ):
93
93
  app = HaikuRAGApp(db_path=db)
94
- asyncio.run(app.add_document_from_source(file_path=file_path))
94
+ asyncio.run(app.add_document_from_source(source=source))
95
95
 
96
96
 
97
97
  @cli.command("get", help="Get and display a document by its ID")
haiku/rag/client.py CHANGED
@@ -319,7 +319,7 @@ class HaikuRAG:
319
319
  return await self.document_repository.list_all(limit=limit, offset=offset)
320
320
 
321
321
  async def search(
322
- self, query: str, limit: int = 5, k: int = 60, rerank=Config.RERANK
322
+ self, query: str, limit: int = 5, k: int = 60
323
323
  ) -> list[tuple[Chunk, float]]:
324
324
  """Search for relevant chunks using hybrid search (vector similarity + full-text search) with reranking.
325
325
 
@@ -331,8 +331,10 @@ class HaikuRAG:
331
331
  Returns:
332
332
  List of (chunk, score) tuples ordered by relevance.
333
333
  """
334
+ # Get reranker if available
335
+ reranker = get_reranker()
334
336
 
335
- if not rerank:
337
+ if reranker is None:
336
338
  return await self.chunk_repository.search_chunks_hybrid(query, limit, k)
337
339
 
338
340
  # Get more initial results (3X) for reranking
@@ -340,7 +342,6 @@ class HaikuRAG:
340
342
  query, limit * 3, k
341
343
  )
342
344
  # Apply reranking
343
- reranker = get_reranker()
344
345
  chunks = [chunk for chunk, _ in search_results]
345
346
  reranked_results = await reranker.rerank(query, chunks, top_n=limit)
346
347
 
haiku/rag/config.py CHANGED
@@ -19,9 +19,8 @@ class AppConfig(BaseModel):
19
19
  EMBEDDINGS_MODEL: str = "mxbai-embed-large"
20
20
  EMBEDDINGS_VECTOR_DIM: int = 1024
21
21
 
22
- RERANK: bool = True
23
- RERANK_PROVIDER: str = "mxbai"
24
- RERANK_MODEL: str = "mixedbread-ai/mxbai-rerank-base-v2"
22
+ RERANK_PROVIDER: str = "ollama"
23
+ RERANK_MODEL: str = "qwen3"
25
24
 
26
25
  QA_PROVIDER: str = "ollama"
27
26
  QA_MODEL: str = "qwen3"
@@ -1,37 +1,40 @@
1
1
  from haiku.rag.config import Config
2
2
  from haiku.rag.reranking.base import RerankerBase
3
3
 
4
- try:
5
- from haiku.rag.reranking.cohere import CohereReranker
6
- except ImportError:
7
- pass
8
-
9
4
  _reranker: RerankerBase | None = None
10
5
 
11
6
 
12
- def get_reranker() -> RerankerBase:
7
+ def get_reranker() -> RerankerBase | None:
13
8
  """
14
9
  Factory function to get the appropriate reranker based on the configuration.
10
+ Returns None if if reranking is disabled.
15
11
  """
16
12
  global _reranker
17
13
  if _reranker is not None:
18
14
  return _reranker
15
+
19
16
  if Config.RERANK_PROVIDER == "mxbai":
20
- from haiku.rag.reranking.mxbai import MxBAIReranker
17
+ try:
18
+ from haiku.rag.reranking.mxbai import MxBAIReranker
21
19
 
22
- _reranker = MxBAIReranker()
23
- return _reranker
20
+ _reranker = MxBAIReranker()
21
+ return _reranker
22
+ except ImportError:
23
+ return None
24
24
 
25
25
  if Config.RERANK_PROVIDER == "cohere":
26
26
  try:
27
27
  from haiku.rag.reranking.cohere import CohereReranker
28
+
29
+ _reranker = CohereReranker()
30
+ return _reranker
28
31
  except ImportError:
29
- raise ImportError(
30
- "Cohere reranker requires the 'cohere' package. "
31
- "Please install haiku.rag with the 'cohere' extra:"
32
- "uv pip install haiku.rag[cohere]"
33
- )
34
- _reranker = CohereReranker()
32
+ return None
33
+
34
+ if Config.RERANK_PROVIDER == "ollama":
35
+ from haiku.rag.reranking.ollama import OllamaReranker
36
+
37
+ _reranker = OllamaReranker()
35
38
  return _reranker
36
39
 
37
- raise ValueError(f"Unsupported reranker provider: {Config.RERANK_PROVIDER}")
40
+ return None
@@ -0,0 +1,84 @@
1
+ import json
2
+
3
+ from ollama import AsyncClient
4
+ from pydantic import BaseModel
5
+
6
+ from haiku.rag.config import Config
7
+ from haiku.rag.reranking.base import RerankerBase
8
+ from haiku.rag.store.models.chunk import Chunk
9
+
10
+ OLLAMA_OPTIONS = {"temperature": 0.0, "seed": 42, "num_ctx": 16384}
11
+
12
+
13
+ class RerankResult(BaseModel):
14
+ """Individual rerank result with index and relevance score."""
15
+
16
+ index: int
17
+ relevance_score: float
18
+
19
+
20
+ class RerankResponse(BaseModel):
21
+ """Response from the reranking model containing ranked results."""
22
+
23
+ results: list[RerankResult]
24
+
25
+
26
+ class OllamaReranker(RerankerBase):
27
+ def __init__(self, model: str = Config.RERANK_MODEL):
28
+ self._model = model
29
+ self._client = AsyncClient(host=Config.OLLAMA_BASE_URL)
30
+
31
+ async def rerank(
32
+ self, query: str, chunks: list[Chunk], top_n: int = 10
33
+ ) -> list[tuple[Chunk, float]]:
34
+ if not chunks:
35
+ return []
36
+
37
+ documents = []
38
+ for i, chunk in enumerate(chunks):
39
+ documents.append({"index": i, "content": chunk.content})
40
+
41
+ # Create the prompt for reranking
42
+ system_prompt = """You are a document reranking assistant. Given a query and a list of document chunks, you must rank them by relevance to the query.
43
+
44
+ Return your response as a JSON object with a "results" array. Each result should have:
45
+ - "index": the original index of the document (integer)
46
+ - "relevance_score": a score between 0.0 and 1.0 indicating relevance (float, where 1.0 is most relevant)
47
+
48
+ Only return the top documents up to the requested limit, ordered by decreasing relevance score."""
49
+
50
+ documents_text = ""
51
+ for doc in documents:
52
+ documents_text += f"Index {doc['index']}: {doc['content']}\n\n"
53
+
54
+ user_prompt = f"""Query: {query}
55
+
56
+ Documents to rerank:
57
+ {documents_text.strip()}
58
+
59
+ Please rank these documents by relevance to the query and return the top {top_n} results as JSON."""
60
+
61
+ messages = [
62
+ {"role": "system", "content": system_prompt},
63
+ {"role": "user", "content": user_prompt},
64
+ ]
65
+
66
+ try:
67
+ response = await self._client.chat(
68
+ model=self._model,
69
+ messages=messages,
70
+ format=RerankResponse.model_json_schema(),
71
+ options=OLLAMA_OPTIONS,
72
+ )
73
+
74
+ content = response["message"]["content"]
75
+
76
+ parsed_response = RerankResponse.model_validate(json.loads(content))
77
+ return [
78
+ (chunks[result.index], result.relevance_score)
79
+ for result in parsed_response.results[:top_n]
80
+ ]
81
+
82
+ except Exception:
83
+ # Fallback: return chunks in original order with same score
84
+ return [(chunks[i], 1.0) for i in range(min(top_n, len(chunks)))]
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: haiku.rag
3
- Version: 0.5.1
3
+ Version: 0.5.2
4
4
  Summary: Retrieval Augmented Generation (RAG) with SQLite
5
5
  Author-email: Yiorgis Gozadinos <ggozadinos@gmail.com>
6
6
  License: MIT
@@ -21,8 +21,7 @@ Requires-Python: >=3.11
21
21
  Requires-Dist: docling>=2.15.0
22
22
  Requires-Dist: fastmcp>=2.8.1
23
23
  Requires-Dist: httpx>=0.28.1
24
- Requires-Dist: mxbai-rerank>=0.1.6
25
- Requires-Dist: ollama>=0.5.1
24
+ Requires-Dist: ollama>=0.5.3
26
25
  Requires-Dist: pydantic>=2.11.7
27
26
  Requires-Dist: python-dotenv>=1.1.0
28
27
  Requires-Dist: rich>=14.0.0
@@ -34,6 +33,8 @@ Provides-Extra: anthropic
34
33
  Requires-Dist: anthropic>=0.56.0; extra == 'anthropic'
35
34
  Provides-Extra: cohere
36
35
  Requires-Dist: cohere>=5.16.1; extra == 'cohere'
36
+ Provides-Extra: mxbai
37
+ Requires-Dist: mxbai-rerank>=0.1.6; extra == 'mxbai'
37
38
  Provides-Extra: openai
38
39
  Requires-Dist: openai>=1.0.0; extra == 'openai'
39
40
  Provides-Extra: voyageai
@@ -1,9 +1,9 @@
1
1
  haiku/rag/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
2
- haiku/rag/app.py,sha256=FpLVyP1-zAq_XPmU8CPVLkuIAeuhBOGvMqhYS8RbN40,7649
2
+ haiku/rag/app.py,sha256=kuvULOIdgwqzJMaKtb1znStc1YAqB1-RkZ0fwdg6TBk,7642
3
3
  haiku/rag/chunker.py,sha256=PVe6ysv8UlacUd4Zb3_8RFWIaWDXnzBAy2VDJ4TaUsE,1555
4
- haiku/rag/cli.py,sha256=rk4uUwN_FdMC-rai9_R2sgXXMI3TIWKRtdWWHg_WoWM,5865
5
- haiku/rag/client.py,sha256=pFcrPkQo1h1zJ76jts-72goP_kGVtnJNfLuoT8qpsb8,15795
6
- haiku/rag/config.py,sha256=8mlQ8gYFxxq1q9gi9tjY9StjqhfhiHkO1FvS4b0et0E,1633
4
+ haiku/rag/cli.py,sha256=5CcWcBQ47KCZ1wl7DpLzMXtgJZ1nz5Hci8AYp72oXEI,5855
5
+ haiku/rag/client.py,sha256=K51l_orUc3BeKGTHX4xC7YClY9M4Eijpac5Hg1_q6LE,15815
6
+ haiku/rag/config.py,sha256=jiy5vg-YbYa7yY-834Dd9omFtfMBXQBYXmHRJXMPjrs,1581
7
7
  haiku/rag/logging.py,sha256=zTTGpGq5tPdcd7RpCbd9EGw1IZlQDbYkrCg9t9pqRc4,580
8
8
  haiku/rag/mcp.py,sha256=tMN6fNX7ZtAER1R6DL1GkC9HZozTC4HzuQs199p7icI,4551
9
9
  haiku/rag/monitor.py,sha256=r386nkhdlsU8UECwIuVwnrSlgMk3vNIuUZGNIzkZuec,2770
@@ -20,10 +20,11 @@ haiku/rag/qa/base.py,sha256=4ZTM_l5FAZ9cA0f8NeqRJiUAmjatwCTmSoclFw0gTFQ,1349
20
20
  haiku/rag/qa/ollama.py,sha256=EGUi4urSx9nrnsr5j-qHVDVOnvRTbSMKUbMvXEMIcxM,2381
21
21
  haiku/rag/qa/openai.py,sha256=dF32sGgVt8mZi5oVxByaeECs9NqLjvDiZnnpJBsrHm8,3968
22
22
  haiku/rag/qa/prompts.py,sha256=8uYMxHzbzI9vo2FPkCSSNTh_RNL96WkBbUWPCMBlLpo,1315
23
- haiku/rag/reranking/__init__.py,sha256=DsPCdU94wRzDCYl6hz2DySOMWwOvNxKviqKAUfyykK8,1118
23
+ haiku/rag/reranking/__init__.py,sha256=fwC3pauteJwh9Ulm2270QvwAdwr4NMr4RUEuolC-wKU,1063
24
24
  haiku/rag/reranking/base.py,sha256=LM9yUSSJ414UgBZhFTgxGprlRqzfTe4I1vgjricz2JY,405
25
25
  haiku/rag/reranking/cohere.py,sha256=1iTdiaa8vvb6oHVB2qpWzUOVkyfUcimVSZp6Qr4aq4c,1049
26
26
  haiku/rag/reranking/mxbai.py,sha256=46sVTsTIkzIX9THgM3u8HaEmgY7evvEyB-N54JTHvK8,867
27
+ haiku/rag/reranking/ollama.py,sha256=tCrLlNNDBCZu7J3to1gvBq-sOvN1flYEA7E3H3Jq0mU,2790
27
28
  haiku/rag/store/__init__.py,sha256=hq0W0DAC7ysqhWSP2M2uHX8cbG6kbr-sWHxhq6qQcY0,103
28
29
  haiku/rag/store/engine.py,sha256=cOMBToLilI1Di1qQrFzGLqtRMsuvtiX0Q5RNIEzQy9w,6232
29
30
  haiku/rag/store/models/__init__.py,sha256=s0E72zneGlowvZrFWaNxHYjOAUjgWdLxzdYsnvNRVlY,88
@@ -36,8 +37,8 @@ haiku/rag/store/repositories/document.py,sha256=ki8LiDukwU1469Yw51i0rQFvBzUQeYkF
36
37
  haiku/rag/store/repositories/settings.py,sha256=qZLXvLsErnCWL0nBQQNfRnatHzCKhtUDLvUK9k-W_fU,2463
37
38
  haiku/rag/store/upgrades/__init__.py,sha256=kKS1YWT_P-CYKhKtokOLTIFNKf9jlfjFFr8lyIMeogM,100
38
39
  haiku/rag/store/upgrades/v0_3_4.py,sha256=GLogKZdZ40NX1vBHKdOJju7fFzNUCHoEnjSZg17Hm2U,663
39
- haiku_rag-0.5.1.dist-info/METADATA,sha256=X4r-1CBCTef3_T9HWPgCHi5XumqOSF4tlHfUpxO533E,4198
40
- haiku_rag-0.5.1.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
41
- haiku_rag-0.5.1.dist-info/entry_points.txt,sha256=G1U3nAkNd5YDYd4v0tuYFbriz0i-JheCsFuT9kIoGCI,48
42
- haiku_rag-0.5.1.dist-info/licenses/LICENSE,sha256=eXZrWjSk9PwYFNK9yUczl3oPl95Z4V9UXH7bPN46iPo,1065
43
- haiku_rag-0.5.1.dist-info/RECORD,,
40
+ haiku_rag-0.5.2.dist-info/METADATA,sha256=b91HARmgPKSy_4LIhna9EoacKb9I_f-cRRTgHqaG-S8,4238
41
+ haiku_rag-0.5.2.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
42
+ haiku_rag-0.5.2.dist-info/entry_points.txt,sha256=G1U3nAkNd5YDYd4v0tuYFbriz0i-JheCsFuT9kIoGCI,48
43
+ haiku_rag-0.5.2.dist-info/licenses/LICENSE,sha256=eXZrWjSk9PwYFNK9yUczl3oPl95Z4V9UXH7bPN46iPo,1065
44
+ haiku_rag-0.5.2.dist-info/RECORD,,