
    0iG                        d Z ddlZddlZddlZddlZddlmZ ddlZddlZddl	m
Z
 ddlmZ  ej                  dd      ZdZd	Zd
Ze
	 d5deedf   deedf   defd       Ze
	 d6deedf   deedf   defd       ZdedefdZdee   dee   fdZe
	 d7deedf   deedf   defd       ZdZdd eeeegd!Ze
	 d8deedf   deed#f   defd$       Zej=                  d%d&      Zded'   eeeegd!Z e!d(k(  rv e"d)       ejG                  d*d+d,      Z$ e"e$dd-         e"d.       ejG                  d/d0d1      Z$ e"e$dd-         e"d2       ejG                  d3d"d4      Z$ e"e$dd0        yy)9u  
Jina AI Tools for DeepAgents
=============================
Tool 1: jina_search  — s.jina.ai  语义网络搜索（返回 top-N 结构化结果）
Tool 2: jina_reader  — r.jina.ai  单 URL 全文提取（返回 Markdown）
Tool 3: jina_deepsearch — deepsearch.jina.ai  深度研究（流式，返回带引用的文章）

SubAgent: jina-writer  — deepagents 兼容的文章撰写子 agent
    N)	Annotated)tool)get_stream_writerJINA_API_KEY zhttps://s.jina.ai/zhttps://r.jina.ai/z.https://deepsearch.jina.ai/v1/chat/completionsqueryu/   Search query — describe what you want to findnum_resultsz-Number of results to return (1-10, default 5)returnc                    dt          dddd}| t        dt        d|            d}	 t        j                  t
        ||d	
      }|j                          |j                         }|j                  dg       }|syg }t        |d      D ]  \  }	}
|
j                  dd      }|
j                  dd      }|
j                  d      xs |
j                  d      xs dj                         }|dd t        |      dkD  rdndz   }|j                  d|	 d| d| d|         dj                  |      S # t        j                  $ r}d| cY d}~S d}~ww xY w)a  Search the web using Jina AI (s.jina.ai).

    Returns top results as LLM-friendly markdown with title, URL, and content.
    Use this for: current events, factual lookup, finding primary sources.
    Each result is capped at 2000 chars to stay within context limits.
    Bearer application/jsontruemarkdown)AuthorizationAcceptX-With-Links-SummaryX-Return-Format   
   )qnum   )headersjsontimeoutz[jina_search error] NdatazNo results found.titleUntitledurlr   contentdescriptioni  u   …[z] **z**
URL: 

z

---

)r   maxminrequestspost_SEARCH_URLraise_for_statusr   RequestExceptionget	enumeratestriplenappendjoin)r   r	   r   payloadrespr   eitemspartsiitemr   r   r    s                 +/home/yzq/tmp/tech/deepagents/jina_tools.pyjina_searchr9       sp    #<.1$ &%	G 1c"k*+G

*}}	
 	yy{ HHVR E"EUA& D4*-hhub!88I&G$((=*AGRNNP%4.S\D-@EbIq4wiuD	BCD e$$ $$ *%aS))*s   =D1 1EEEEr   z9Full URL of the page to read (must start with http/https)	max_charsz'Max characters to return (default 6000)c                    | j                  d      sydt         dddd}	 t        j                  t         |  |d	      }|j                          |j                         }|j                  di       }|j                  d|       }|j                  d      xs dj                         }|sd|  S |d| t        |      |kD  rdndz   }	d| d|  d|	 S # t        j                  $ r}d
| cY d}~S d}~ww xY w)a4  Read and extract clean Markdown content from a URL using Jina AI (r.jina.ai).

    Use this for: reading a specific article, report, or document in full;
    following up on a search result; extracting structured content from a page.
    Returns the page title + full markdown body, capped at max_chars.
    httpz;[jina_reader error] URL must start with http:// or https://r   r   r   false)r   r   r   r   r   )r   r   z[jina_reader error] Nr   r   r    r   z([jina_reader] No content extracted from u   …[truncated]z# z	
Source: r#   )

startswithr   r&   r+   _READER_URLr)   r   r*   r-   r.   )
r   r:   r   r2   r   r3   r1   r   r    	truncateds
             r8   jina_readerrA   U   s    >>&!L #<.1$% '	G	*||mC5!

 	yy{ hhvr"GKK%E{{9%+224G9#??
#3w<);S'7Y[\IwjT)55 $$ *%aS))*s   A C C5&C0*C50C5textc                 l    t        j                  dd| t         j                        j                         S )zBRemove <think>...</think> reasoning blocks from DeepSearch output.z<think>.*?</think>r   )flags)resubDOTALLr-   )rB   s    r8   _strip_thinkingrH      s%    66'TCIIKK    	citationsc                     t               g }}| D ]>  }|j                  dd      }|s||vs|j                  |       |j                  |       @ |S )Nr   r   )setr+   addr/   )rJ   seenuniquecr   s        r8   _dedupe_citationsrQ      sS    5"&D eeE23d?HHSMMM!	
 MrI   z1Research question or article topic to investigatereasoning_effortz[Depth of research: 'low' (fast, ~30s), 'medium' (balanced, ~1min), 'high' (thorough, ~3min)c           	      6   dt          ddd}dd| dgd|dd	}d
}g }	 t        j                  t        ||dd      5 }|j	                          |j                         D ]=  }|st        |t              r|j                  d      n|}|j                  d      s<|dd j                         }	|	dk(  r n	 t        j                  |	      }
|
j                  d      xs i gd   }|j                  di       }|j                  d      xs d
}|r||z  }|j                  d      xs |
j                  d      xs g D ]`  }t        |t              s|j                  d      dk(  s)|j                  d      xs |}|j                  d      sP|j                  |       b @ ddd       |syt'        |      }t)        |      }t+        j,                  d|t*        j.                        }|ra|s_|dz  }t1        |d      D ]K  \  }}|j                  d      xs |j                  dd
      }|j                  dd
      }|d | d!| d"| d#z  }M |S # t        j                   t"        f$ r Y w xY w# 1 sw Y   xY w# t        j$                  $ r}d| cY d}~S d}~ww xY w)$u,  Conduct deep web research using Jina AI DeepSearch.

    Autonomously plans search strategies, reads multiple sources, reasons over
    evidence, and returns a well-cited research synthesis or article.

    Use this for:
    - Writing comprehensive articles or reports
    - Multi-source research requiring synthesis
    - Questions needing up-to-date information with citations

    Returns the full research result with inline citations and a Sources section.
    NOTE: This tool is slow (30s – 3min). Use reasoning_effort='low' for quick lookups.
    r   r   text/event-streamr   zContent-Typer   jina-deepsearch-v1userroler    TmodelmessagesstreamrR   no_direct_answerr   ,  )r   r   r]   r   zutf-8data:    N[DONE]choicesr   deltar    annotationstypeurl_citationr   z[jina_deepsearch error] z&[jina_deepsearch] No content returned.u   ^## (Sources|References|参考)

## Sources
r   r   r"   ]     — 
)r   r&   r'   _DEEPSEARCH_URLr)   
iter_lines
isinstancebytesdecoder>   r-   r   loadsr+   dictr/   JSONDecodeErrorKeyErrorr*   rH   rQ   rE   search	MULTILINEr,   )r   rR   r   r1   full_contentrJ   r2   raw_linelinedata_strchunkchoicerd   content_pieceannucr3   answerunique_citationshas_sourcesr6   rP   r   r   s                           r8   jina_deepsearchr      s   , #<.1*%G &$78, G LI*.]]
 &	 !!# OO- 3=h3Nxw/T\x08>>+x' JJx0E#ii	2:rdA>F"JJw3E %*IIi$8$>BM$$5 !&		- 8 ZEIIm<T ZXZ 5)#t4$776?n<!$!8!?CB!vve} ) 0 0 45+&	V 7 \*F )3))>UK$$.2 	3DAqEE'N6aeeE2&6E%%r"C!BugU3%r22F	3
 M- ,,h7 K&	 &	P $$ .)!--.sf   I6 A7I*5B,I
"&I
	I
I*I6 
I'#I*&I''I**I3/I6 6J	JJJu	  You are an expert research writer powered by Jina AI.

## Role
Given a writing request (article, report, analysis, summary), you:
1. Research the topic thoroughly using jina_deepsearch
2. Optionally deepen specific angles using jina_search + jina_reader
3. Synthesize all findings into a well-structured, citation-backed piece

## Tools Available
- `jina_deepsearch(query, reasoning_effort)` — primary: deep multi-source research with citations
- `jina_search(query, num_results)` — supplement: targeted keyword searches
- `jina_reader(url)` — supplement: read a specific source in full

## Writing Process

### Step 1 — Understand the request
Identify: topic scope, target length, required sections, target audience, tone (technical / general).

### Step 2 — Research
- Call `jina_deepsearch` with the core topic
  - Use `reasoning_effort="high"` for long-form articles or reports (>1000 words)
  - Use `reasoning_effort="medium"` for standard pieces
  - Use `reasoning_effort="low"` for quick summaries
- If specific sub-topics need more depth, call `jina_search` then `jina_reader` on key URLs

### Step 3 — Write the article
Synthesize all research into a coherent piece. Structure:
```
# [Title]

## Introduction / Executive Summary

## [Section 1]
[content with inline citations [1][2]]

## [Section 2 … N]

## Conclusion / Key Takeaways

## References
[1] Title — URL
[2] ...
```

## Citation Rules
- Every factual claim must carry an inline citation: [1], [2], etc.
- Consolidate all URLs into a References section at the end
- Do not fabricate sources — only cite what jina_deepsearch or jina_reader actually returned

## Output
Return the complete article in Markdown. Do NOT return a raw dump of DeepSearch output —
write a proper article that synthesizes the research.
zjina-writera*  Writes comprehensive, citation-backed articles and research reports using Jina AI DeepSearch for up-to-date web research. Use for: long-form articles, market research, topic overviews, technical summaries requiring current sources. Pass: article topic, desired length/sections, and target audience.)namer!   system_prompttoolslowz5Depth: 'low' (~60s), 'medium' (~3min), 'high' (~5min)c                 4  K   t               }dt         ddd}dd| dgd|dd	}d
}g }d}d
}	 t        j                  d      4 d{   }	|	j	                  dt
        ||      4 d{   }
|
j                          |
j                         2 3 d{   }|j                  d      s|dd j                         }|dk(  r n	 t        j                  |      }|j                  d      xs i gd   }|j                  di       }|j                  d      xs d
}|r:||z  }|s+||z  }d|v r*d}|j                  dd      d   }|r ||       n ||       |j                  d      xs |j                  d      xs g D ]`  }t        |t              s|j                  d      dk(  s)|j                  d      xs |}|j                  d      sP|j!                  |       b Uddd      d{    ddd      d{    |syt+        |      }t-        |      }|r}t/        j0                  d |t.        j2                        sX|d!z  }t5        |d      D ]D  \  }}|d"| d#|j                  d$|j                  dd
             d%|j                  dd
       d&z  }F |S 7 V7 77 # t        j"                  t$        t&        f$ r Y 9w xY w6 7 # 1 d{  7  sw Y   xY w7 # 1 d{  7  sw Y   xY w# t(        $ r}d| cY d}~S d}~ww xY ww)'aM  Deep web research with REAL-TIME streaming output.

    Uses Jina AI DeepSearch and pushes answer tokens to the stream as they
    arrive via get_stream_writer(). The <think> reasoning block is suppressed;
    only the final answer content streams out.

    Use this instead of jina_deepsearch when the caller needs live output.
    r   r   rT   rU   rV   rW   rX   TrZ   r   Fr_   )r   NPOST)r   r   r`   ra   rb   rc   r   rd   r    z</think>r   re   rf   rg   r   z[jina_deepsearch_stream error] z-[jina_deepsearch_stream] No content returned.z^## (Sources|References)rh   r"   ri   r   rj   rk   )r   r   httpxAsyncClientr]   rl   r)   aiter_linesr>   r-   r   rq   r+   splitrn   rr   r/   rs   rt   
IndexError	ExceptionrH   rQ   rE   ru   rv   r,   )r   rR   writer   r1   rw   rJ   thinking_done	think_bufclientr2   rx   rz   r{   r|   rd   pieceafterr~   r   r3   r   rO   r6   rP   s                            r8   jina_deepsearch_streamr   D  sH      E #<.1*%G &$78, G LI MI*5$$S1 &	! &	!V}}w %  %! %!%%'&*&6&6&8 !! !!(#..x8 '|113H8+! $

8 4"'))I"6">2$!B &

7B 7 %		) 4 : (E1L#0 )U 2	#-#:48M,5OOJ,J1,ME',(-e %e %*IIm$<$^		-@X$^\^ 9C)#t4N9Z%(WW^%<%C#%66%=$-$4$4R$8	9=%! %!&	! &	!V >\*Fy)Fbii ;VR\\R$$fa( 	YDAq!BquuWaeeE"o>?uQUU5QS_DUUWXXF	Y Mk&	!%!!!@ !00(JG ! !A '9	%! %! %! %!&	! &	! &	! &	!P  50445s  ,LK= 	J
K= K(+J",K(/!KKJ%
K.KCJ(J()&J(J(#K%K(0K1K(5K=  K&K= BLK= "K(%K(K
	K	K
	
KK(K#	KK#	K(&K= (K:.K1/K:6K= =	LL
LLLLz(jina_deepsearch(query, reasoning_effort)z/jina_deepsearch_stream(query, reasoning_effort)r!   __main__z=== jina_search ===zJina AI DeepSearch API 2025   )r   r	   i  z
=== jina_reader ===zhttps://jina.ai/deepsearchi  )r   r:   z
=== jina_deepsearch ===zMWhat are the key differences between RAG and DeepSearch for LLM applications?)r   rR   )   )ip  )medium)r   )%__doc__asyncior   osrE   typingr   r   r&   langchain_core.toolsr   langgraph.configr   getenvr   r(   r?   rl   strintr9   rA   rH   listrr   rQ   r   JINA_WRITER_INSTRUCTIONSjina_writer_subagentr   replaceJINA_WRITER_STREAM_INSTRUCTIONSjina_writer_stream_subagent__name__printinvokeresult rI   r8   <module>r      s     	 	    % .ryy,""B  TU-%SKKL-%3 OOP-% 	-% -%h  LP'6	3SS	T'6GGH'6 	'6 '6\L# L# L
d T
   	`SMMN`e	g` 	` `P4  n 	M .{K8 $  	[SMMN[?	A[ 	[ [~ #;"B"B.5#  '64$k;?	  z	
 *GXY Z[F	&#, 

!"(DSW XYF	&#, 

%&##`!% F 
&$-# rI   