<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Gate of AI</title>
    <description>The latest articles on DEV Community by Gate of AI (@gateofai).</description>
    <link>https://dev.to/gateofai</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F3946864%2Fb6132c64-945e-41fa-915b-6b3276be957d.png</url>
      <title>DEV Community: Gate of AI</title>
      <link>https://dev.to/gateofai</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/gateofai"/>
    <language>en</language>
    <item>
      <title>Build AI with Claude Sonnet 4.6 &amp; LangChain</title>
      <dc:creator>Gate of AI</dc:creator>
      <pubDate>Sat, 06 Jun 2026 11:56:16 +0000</pubDate>
      <link>https://dev.to/gateofai/build-ai-with-claude-sonnet-46-langchain-lc6</link>
      <guid>https://dev.to/gateofai/build-ai-with-claude-sonnet-46-langchain-lc6</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;🚀 Technical Briefing:&lt;/strong&gt; This tutorial is part of our deep-dive series on Agentic Workflows at &lt;a href="https://gateofai.com" rel="noopener noreferrer"&gt;Gate of AI&lt;/a&gt;. For the full technical breakdown, interactive code sandbox, and the native Arabic translation, visit the &lt;a href="https://gateofai.com/tutorial/build-ai-claude-sonnet-4-6-langchain/" rel="noopener noreferrer"&gt;original article here&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;span&amp;gt;Tutorial&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;Intermediate&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;⏱ 45 min read&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;© Gate of AI 2026-06-06&amp;lt;/span&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;Learn to build a conversational AI application using Claude Sonnet 4.6 and LangChain, leveraging the latest AI advancements for dynamic interactions.&lt;/p&gt;


&lt;h2&gt;Prerequisites&lt;/h2&gt;
&lt;br&gt;
  &lt;ul&gt;

    &lt;li&gt;Python 3.10 or newer&lt;/li&gt;

    &lt;li&gt;Claude Sonnet 4.6 API key&lt;/li&gt;

    &lt;li&gt;Intermediate programming skills&lt;/li&gt;

  &lt;/ul&gt;


&lt;h2&gt;What We're Building&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;In this tutorial, we will construct a conversational AI application using the Claude Sonnet 4.6 model from Anthropic, integrated with LangChain to handle complex dialogues and maintain conversational context. The application will be capable of understanding user input, managing context over long interactions, and providing intelligent responses. Notably, Claude Sonnet 4.6 features a 1M token context window, enhancing its ability to manage extensive conversations.&lt;/p&gt;
&lt;br&gt;
  &lt;p&gt;The finished project will allow users to interact with the AI in a conversational manner, enabling capabilities such as answering questions, providing recommendations, and even executing specific tasks based on user queries. This project demonstrates the power of combining state-of-the-art language models with robust conversational frameworks.&lt;/p&gt;


&lt;h2&gt;Setup and Installation&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;To get started, we'll set up our development environment by installing necessary libraries and configuring our environment variables. This setup ensures that we have all tools required to build and run our application.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;pip install langchain anthropic&lt;/code&gt;&lt;/pre&gt;
&lt;br&gt;
  &lt;p&gt;Next, configure your environment variables to securely store your Claude Sonnet 4.6 API key. This key is essential for authenticating your requests to the Anthropic API.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;
&lt;h1&gt;
  
  
  .env file
&lt;/h1&gt;

&lt;p&gt;CLAUDE_API_KEY=your_claude_sonnet_4_6_api_key_here&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 1: Initialize the LangChain Framework&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;LangChain provides a powerful framework for managing conversation flows and maintaining context. In this step, we initialize LangChain and set up the basic configuration for our conversational AI.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
from langchain import LangChain&lt;br&gt;
from anthropic import Anthropic
&lt;h1&gt;
  
  
  Initialize LangChain
&lt;/h1&gt;

&lt;p&gt;lc = LangChain()&lt;/p&gt;
&lt;h1&gt;
  
  
  Configure LangChain with Claude Sonnet 4.6
&lt;/h1&gt;

&lt;p&gt;client = Anthropic(api_key='your_claude_sonnet_4_6_api_key_here')&lt;br&gt;
lc.add_model('claude-sonnet-4-6', client)&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;br&gt;
  &lt;p&gt;Here, we import the necessary libraries and initialize LangChain. We then configure it to use the Claude Sonnet 4.6 model by providing our API client. This setup is crucial for integrating the language model into our conversation framework.&lt;/p&gt;


&lt;h2&gt;Step 2: Define Conversation Logic&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;In this step, we define the logic that will drive our conversation. This involves setting up handlers for different types of user input and configuring how the AI should respond.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
def handle_greeting(input_text):&lt;br&gt;
    return "Hello! How can I assist you today?"

&lt;p&gt;def handle_farewell(input_text):&lt;br&gt;
    return "Goodbye! Have a great day!"&lt;/p&gt;

&lt;p&gt;def default_handler(input_text):&lt;br&gt;
    # Use Claude Sonnet 4.6 for intelligent responses&lt;br&gt;
    response = client.messages.create(&lt;br&gt;
        model="claude-sonnet-4-6",&lt;br&gt;
        messages=[{"role": "user", "content": input_text}]&lt;br&gt;
    )&lt;br&gt;
    return response.get('content', 'I am sorry, I am unable to process that.')&lt;/p&gt;
&lt;h1&gt;
  
  
  Register handlers
&lt;/h1&gt;

&lt;p&gt;lc.register_handler("greeting", handle_greeting)&lt;br&gt;
lc.register_handler("farewell", handle_farewell)&lt;br&gt;
lc.default_handler = default_handler&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;br&gt;
  &lt;p&gt;In this code block, we define functions to handle greetings and farewells, and a default handler that leverages the Claude Sonnet 4.6 model for more complex interactions. These handlers are registered with LangChain, allowing it to route user inputs to the appropriate logic.&lt;/p&gt;


&lt;h2&gt;Step 3: Implementing the Interaction Loop&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Finally, we implement the main interaction loop that will continuously accept user input and provide responses, creating a seamless conversational experience.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
def run_conversation():&lt;br&gt;
    print("Welcome to the AI chat! Type 'exit' to end the session.")&lt;br&gt;
    while True:&lt;br&gt;
        user_input = input("You: ")&lt;br&gt;
        if user_input.lower() == 'exit':&lt;br&gt;
            print("AI: Goodbye!")&lt;br&gt;
            break&lt;br&gt;
        response = lc.handle_message(user_input)&lt;br&gt;
        print(f"AI: {response}")
&lt;h1&gt;
  
  
  Start the conversation
&lt;/h1&gt;

&lt;p&gt;run_conversation()&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;br&gt;
  &lt;p&gt;This loop continuously prompts the user for input, processes it through LangChain, and prints out the AI's response. The loop will terminate when the user types 'exit', providing a clean and user-friendly interaction.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;⚠️ Common Mistake:&lt;/strong&gt; Ensure your API keys are correctly configured in the environment variables. Failing to do so will result in authentication errors when trying to access the Claude API.&lt;/p&gt;


&lt;h2&gt;Testing Your Implementation&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;To verify that your conversational AI is working correctly, initiate the interaction loop and test various inputs. You should expect intelligent and contextually appropriate responses from the AI.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;
&lt;h1&gt;
  
  
  Test the conversation by running the script
&lt;/h1&gt;

&lt;p&gt;python your_script_name.py&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;
&lt;br&gt;
  &lt;p&gt;During testing, ensure that the AI can handle various types of input and maintains context across interactions. This will validate the effectiveness of your LangChain setup and the integration with Claude Sonnet 4.6.&lt;/p&gt;


&lt;h2&gt;What to Build Next&lt;/h2&gt;
&lt;br&gt;
  &lt;ul&gt;

    &lt;li&gt;Integrate voice input and output to create a voice-enabled assistant.&lt;/li&gt;

    &lt;li&gt;Expand your AI's capabilities by adding more specialized handlers for specific tasks.&lt;/li&gt;

    &lt;li&gt;Deploy your application as a web service using frameworks like FastAPI or Flask.&lt;/li&gt;

  &lt;/ul&gt;
&lt;br&gt;
  &lt;p&gt;Consider how such applications can be integrated into regional initiatives like Saudi Vision 2030 or the UAE's National Strategy for AI, enhancing local technological infrastructure and capabilities.&lt;/p&gt;

</description>
      <category>webdev</category>
      <category>ai</category>
      <category>tutorial</category>
      <category>discuss</category>
    </item>
    <item>
      <title>Build a Conversational AI with LlamaIndex</title>
      <dc:creator>Gate of AI</dc:creator>
      <pubDate>Thu, 04 Jun 2026 15:22:31 +0000</pubDate>
      <link>https://dev.to/gateofai/build-a-conversational-ai-with-llamaindex-27go</link>
      <guid>https://dev.to/gateofai/build-a-conversational-ai-with-llamaindex-27go</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;🚀 Technical Briefing:&lt;/strong&gt; This tutorial is part of our deep-dive series on Agentic Workflows at &lt;a href="https://gateofai.com" rel="noopener noreferrer"&gt;Gate of AI&lt;/a&gt;. For the full technical breakdown, interactive code sandbox, and the native Arabic translation, visit the &lt;a href="https://gateofai.com/tutorial/build-conversational-ai-llamaindex/" rel="noopener noreferrer"&gt;original article here&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;span&amp;gt;Tutorial&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;Intermediate&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;⏱ 20 min read&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;© Gate of AI 2026-06-04&amp;lt;/span&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;Learn to build an intelligent conversational AI agent by leveraging LlamaIndex to dynamically orchestrate and route prompts between OpenAI and Anthropic APIs.&lt;/p&gt;


&lt;h2&gt;Prerequisites&lt;/h2&gt;
&lt;br&gt;
  &lt;ul&gt;

    &lt;li&gt;Python 3.10 or newer&lt;/li&gt;

    &lt;li&gt;API keys for OpenAI and Anthropic&lt;/li&gt;

    &lt;li&gt;Intermediate knowledge of Python and asynchronous programming&lt;/li&gt;

  &lt;/ul&gt;


&lt;h2&gt;What We're Building&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;In this tutorial, we will construct an agentic conversational AI companion using &lt;strong&gt;LlamaIndex&lt;/strong&gt;. Instead of using primitive hardcoded logic to route user intent, we will use a ReAct (Reasoning and Acting) agent loop. This workflow allows the core engine to evaluate a user's prompt and dynamically choose whether to delegate the task to OpenAI's GPT-4o or Anthropic's Claude 3.5 Sonnet.&lt;/p&gt;


&lt;h2&gt;Setup and Installation&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Modern versions of LlamaIndex are modular. We must install the core framework alongside the specific multi-model provider integration packages.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;pip install llama-index llama-index-llms-openai llama-index-llms-anthropic python-dotenv&lt;/code&gt;&lt;/pre&gt;
&lt;br&gt;
  &lt;p&gt;Next, configure your environment variables securely. Create a &lt;code&gt;.env&lt;/code&gt; file in your root project directory:&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;
&lt;h1&gt;
  
  
  .env file
&lt;/h1&gt;

&lt;p&gt;OPENAI_API_KEY=your_openai_api_key&lt;br&gt;
ANTHROPIC_API_KEY=your_anthropic_api_key&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 1: Initializing LLMs with LlamaIndex Abstractions&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;First, we configure our environment and initialize our language models using the official LlamaIndex wrappers. This standardizes their inputs and outputs.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
import os&lt;br&gt;
import asyncio&lt;br&gt;
from dotenv import load_dotenv&lt;br&gt;
from llama_index.llms.openai import OpenAI&lt;br&gt;
from llama_index.llms.anthropic import Anthropic

&lt;p&gt;load_dotenv()&lt;/p&gt;
&lt;h1&gt;
  
  
  Instantiate the respective LLM configurations
&lt;/h1&gt;

&lt;p&gt;gpt_model = OpenAI(model="gpt-4o")&lt;br&gt;
claude_model = Anthropic(model="claude-3-5-sonnet-20241022")&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 2: Defining Functional Agent Tools&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;To let our agent interact with these models dynamically, we wrap the model invocations inside LlamaIndex &lt;code&gt;FunctionTool&lt;/code&gt; structures. The docstrings act as the prompt-hints the agent reads to make its structural decisions.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
from llama_index.core.tools import FunctionTool

&lt;p&gt;def call_gpt_engine(prompt: str) -&amp;gt; str:&lt;br&gt;
    """Useful when queries require raw logic, structured JSON formatting, or math calculations."""&lt;br&gt;
    response = gpt_model.complete(prompt)&lt;br&gt;
    return str(response)&lt;/p&gt;

&lt;p&gt;def call_claude_engine(prompt: str) -&amp;gt; str:&lt;br&gt;
    """Useful when queries require deeply creative writing, code generation, or nuanced tonal analysis."""&lt;br&gt;
    response = claude_model.complete(prompt)&lt;br&gt;
    return str(response)&lt;/p&gt;
&lt;h1&gt;
  
  
  Convert functions to native tools
&lt;/h1&gt;

&lt;p&gt;gpt_tool = FunctionTool.from_defaults(fn=call_gpt_engine)&lt;br&gt;
claude_tool = FunctionTool.from_defaults(fn=call_claude_engine)&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 3: Creating the ReAct Agent&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Now, we construct the &lt;code&gt;ReActAgent&lt;/code&gt;, passing our custom model tools directly into its execution layout. We will use GPT-4o as our central engine coordinator.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
from llama_index.core.agent import ReActAgent
&lt;h1&gt;
  
  
  Bind tools to the orchestration framework
&lt;/h1&gt;

&lt;p&gt;tools = [gpt_tool, claude_tool]&lt;br&gt;
agent = ReActAgent.from_tools(tools, llm=gpt_model, verbose=True)&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;&lt;strong&gt;⚠️ Architecture Reminder:&lt;/strong&gt; Ensure you are using separate packages like &lt;code&gt;llama-index-llms-openai&lt;/code&gt;. Importing directly from a legacy global namespace will result in structural &lt;code&gt;ModuleNotFoundError&lt;/code&gt; crashes.&lt;/p&gt;


&lt;h2&gt;Testing Your Implementation&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Execute queries targeting different tasks to see LlamaIndex evaluate the text, pick a tool, format its variables, and cleanly handle responses.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
async def main():&lt;br&gt;
    # This should trigger the Claude tool based on your docstring hints&lt;br&gt;
    creative_res = await agent.achat("Write a short, moody poem about artificial intelligence.")&lt;br&gt;
    print(f"Creative Task:\n{creative_res}\n")
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# This should route to the GPT tool
structured_res = await agent.achat("Generate a structured list of 3 fake user profiles with keys: id, name.")
print(f"Structured Task:\n{structured_res}\n")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;if &lt;strong&gt;name&lt;/strong&gt; == "&lt;strong&gt;main&lt;/strong&gt;":&lt;br&gt;
    asyncio.run(main())&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;What to Build Next&lt;/h2&gt;
&lt;br&gt;
  &lt;ul&gt;

    &lt;li&gt;Add a &lt;code&gt;VectorStoreIndex&lt;/code&gt; to supply localized RAG context windows straight to your tool execution pathways.&lt;/li&gt;

    &lt;li&gt;Incorporate persistent database storage to preserve chat histories across multiple app sessions.&lt;/li&gt;

    &lt;li&gt;Expose your LlamaIndex orchestration wrapper via a robust FastAPI framework backend.&lt;/li&gt;

  &lt;/ul&gt;

</description>
      <category>webdev</category>
      <category>ai</category>
      <category>tutorial</category>
      <category>discuss</category>
    </item>
    <item>
      <title>Build a RAG System with OpenAI &amp; Pinecone</title>
      <dc:creator>Gate of AI</dc:creator>
      <pubDate>Thu, 04 Jun 2026 15:15:35 +0000</pubDate>
      <link>https://dev.to/gateofai/build-a-rag-system-with-openai-pinecone-511</link>
      <guid>https://dev.to/gateofai/build-a-rag-system-with-openai-pinecone-511</guid>
      <description>&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F25d2fw3h9se3b9jhe588.jpg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F25d2fw3h9se3b9jhe588.jpg" alt=" " width="800" height="437"&gt;&lt;/a&gt;&amp;gt; &lt;strong&gt;🚀 Technical Briefing:&lt;/strong&gt; This tutorial is part of our deep-dive series on Agentic Workflows at &lt;a href="https://gateofai.com" rel="noopener noreferrer"&gt;Gate of AI&lt;/a&gt;. For the full technical breakdown, interactive code sandbox, and the native Arabic translation, visit the &lt;a href="https://gateofai.com/tutorial/build-rag-system-openai-pinecone/" rel="noopener noreferrer"&gt;original article here&lt;/a&gt;.&lt;/p&gt;

&lt;h1&gt;Building a Modern Retrieval-Augmented Generation (RAG) System with OpenAI and Pinecone&lt;/h1&gt;

&lt;p&gt;Learn how to build a state-of-the-art Retrieval-Augmented Generation (RAG) system using OpenAI's GPT models and Pinecone for efficient information retrieval and generation. This tutorial will guide you through setting up a system that combines the power of language models with vector databases to retrieve relevant information and generate contextually rich responses, incorporating the latest advancements in RAG technology.&lt;/p&gt;

&lt;h2&gt;Prerequisites&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Python 3.10 or above&lt;/li&gt;



&lt;li&gt;OpenAI API key&lt;/li&gt;



&lt;li&gt;Pinecone account and API key&lt;/li&gt;



&lt;li&gt;Intermediate knowledge of Python and RESTful APIs&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;What We're Building&lt;/h2&gt;

&lt;p&gt;In this tutorial, you'll learn how to build a Retrieval-Augmented Generation (RAG) system. This system combines the power of OpenAI's language models with Pinecone's vector database to retrieve relevant information and generate contextually rich responses. The RAG system is designed to handle unstructured data and provide accurate, detailed answers by leveraging both retrieval and generation capabilities. By the end of this tutorial, you will have a fully functional RAG system that can be used in various applications, such as customer support, knowledge management, and more. The system will retrieve relevant documents from a vector database and use a language model to generate coherent and informative responses.&lt;/p&gt;

&lt;h2&gt;Setup and Installation&lt;/h2&gt;

&lt;p&gt;We will begin by setting up our development environment. This involves installing the necessary Python packages and configuring environment variables for API access.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;pip install openai pinecone&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Next, we need to configure our environment variables. Create a file named &lt;code&gt;.env&lt;/code&gt; in your project directory and add the following variables:&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;OPENAI_API_KEY=your_openai_api_key
PINECONE_API_KEY=your_pinecone_api_key
PINECONE_ENVIRONMENT=your_pinecone_environment&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;These environment variables will allow our application to authenticate with the OpenAI and Pinecone APIs securely.&lt;/p&gt;

&lt;h2&gt;Step 1: Data Preparation and Indexing&lt;/h2&gt;

&lt;p&gt;The first step is to prepare our dataset and index it using Pinecone. We will break our dataset into chunks, compute vector embeddings, and store them in a Pinecone index for efficient retrieval.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;import os
from openai import OpenAI
from pinecone import Pinecone

# Load API keys from environment variables
client = OpenAI(api_key=os.getenv("OPENAI_API_KEY"))
pc = Pinecone(api_key=os.getenv("PINECONE_API_KEY"), environment=os.getenv("PINECONE_ENVIRONMENT"))

# Create a Pinecone index
index_name = "document-index"
index = pc.Index(name=index_name, dimension=1536, metric="cosine")

# Example dataset
documents = ["Document 1 content...", "Document 2 content...", "Document 3 content..."]

# Function to create vector embeddings
def create_embeddings(text):
    response = client.embeddings.create(model="text-embedding-ada-002", input=text)
    return response['data'][0]['embedding']

# Index documents
for i, doc in enumerate(documents):
    embedding = create_embeddings(doc)
    index.upsert([(f"doc_{i}", embedding)])&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;In this step, we initialize the Pinecone client and create an index with a specified dimension and metric. We then generate embeddings for each document using OpenAI's embedding model and upload them to the Pinecone index.&lt;/p&gt;

&lt;h2&gt;Step 2: Implementing the Retrieval Function&lt;/h2&gt;

&lt;p&gt;Next, we implement a function to query the Pinecone index and retrieve documents that are semantically similar to the input query.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;def retrieve_documents(query, top_k=3):
    # Generate query embedding
    query_embedding = create_embeddings(query)
    
    # Query Pinecone index
    results = index.query(query_embedding, top_k=top_k, include_values=True)
    
    # Extract document IDs
    document_ids = [match['id'] for match in results['matches']]
    return document_ids

# Example query
query = "Explain the concept of RAG systems."
retrieved_docs = retrieve_documents(query)
print("Retrieved document IDs:", retrieved_docs)&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;This function takes a query string, generates its embedding, and performs a similarity search in the Pinecone index. The top K matching document IDs are returned, representing the most relevant documents to the query.&lt;/p&gt;

&lt;h2&gt;Step 3: Generating Responses with OpenAI&lt;/h2&gt;

&lt;p&gt;With the relevant documents retrieved, we can now use OpenAI's GPT model to generate a response. This involves constructing a prompt that includes the retrieved documents and the user query.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;def generate_response(query, document_ids):
    # Retrieve document contents
    documents_content = [documents[int(doc_id.split("_")[1])] for doc_id in document_ids]
    
    # Construct prompt
    prompt = f"Given the following documents:\n\n{'\n\n'.join(documents_content)}\n\nAnswer the following question:\n{query}"
    
    # Generate response using OpenAI GPT
    response = client.completions.create(
        model="gpt-4o",
        prompt=prompt,
        max_tokens=200
    )
    return response.choices[0].text.strip()

# Generate a response
response = generate_response(query, retrieved_docs)
print("Generated Response:", response)&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;We retrieve the content of the documents using their IDs, then construct a prompt for the GPT model. The model generates a response based on the combined information from the documents and the query.&lt;/p&gt;

&lt;h2&gt;Testing Your Implementation&lt;/h2&gt;

&lt;p&gt;To verify that our RAG system works correctly, we will test it with various queries and check that the responses are both relevant and informative.&lt;/p&gt;

&lt;pre&gt;&lt;code&gt;# Test with different queries
test_queries = [
    "What is the purpose of retrieval-augmented generation?",
    "How does Pinecone help in information retrieval?",
    "Explain how GPT models generate text."
]

for test_query in test_queries:
    retrieved_docs = retrieve_documents(test_query)
    response = generate_response(test_query, retrieved_docs)
    print(f"Query: {test_query}\nResponse: {response}\n")&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;Run these test queries to ensure that the system retrieves the correct documents and generates accurate responses. Adjust the prompt or retrieval parameters if necessary based on the output quality.&lt;/p&gt;

&lt;h2&gt;What to Build Next&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Enhance the retrieval function to use a hybrid approach combining semantic and keyword search for improved accuracy.&lt;/li&gt;



&lt;li&gt;Integrate a user interface for real-time interaction with the RAG system, allowing users to input queries and receive responses directly.&lt;/li&gt;



&lt;li&gt;Expand the dataset and explore different domain-specific applications, such as medical information retrieval or legal document analysis.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Consider integrating this technology with regional initiatives like Saudi Vision 2030 to enhance AI-driven solutions in the GCC region, leveraging the latest advancements in Dynamic and Parametric RAG for more adaptive and efficient information retrieval systems.&lt;/p&gt;

</description>
      <category>webdev</category>
      <category>ai</category>
      <category>tutorial</category>
      <category>discuss</category>
    </item>
    <item>
      <title>Building an Advanced LangChain AI Workflow Automation with LangGraph</title>
      <dc:creator>Gate of AI</dc:creator>
      <pubDate>Wed, 03 Jun 2026 16:24:19 +0000</pubDate>
      <link>https://dev.to/gateofai/building-an-advanced-langchain-ai-workflow-automation-with-langgraph-345o</link>
      <guid>https://dev.to/gateofai/building-an-advanced-langchain-ai-workflow-automation-with-langgraph-345o</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;🚀 Technical Briefing:&lt;/strong&gt; This tutorial is part of our deep-dive series on Agentic Workflows at &lt;a href="https://gateofai.com" rel="noopener noreferrer"&gt;Gate of AI&lt;/a&gt;. For the full technical breakdown, interactive code sandbox, and the native Arabic translation, visit the &lt;a href="https://gateofai.com/tutorial/langchain-tutorial-advanced-workflow-automation/" rel="noopener noreferrer"&gt;original article here&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;span&amp;gt;Tutorial&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;Advanced&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;⏱ 45 min read&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;© Gate of AI 2026-06-03&amp;lt;/span&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;Build a production-grade multi-agent workflow using LangGraph v1.2. Use state-based orchestration to manage autonomous reasoning loops securely.&lt;/p&gt;


&lt;h2&gt;Prerequisites&lt;/h2&gt;
&lt;br&gt;
  &lt;ul&gt;

    &lt;li&gt;Python 3.10+&lt;/li&gt;

    &lt;li&gt;LangChain v1.3.4+ and LangGraph v1.2.4+&lt;/li&gt;

    &lt;li&gt;OpenAI API Key (GPT-4o)&lt;/li&gt;

    &lt;li&gt;Understanding of Pydantic and TypedDict for state management&lt;/li&gt;

  &lt;/ul&gt;


&lt;h2&gt;Installation&lt;/h2&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;pip install langchain==1.3.4 langgraph==1.2.4 langchain-openai&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 1: Define the State Schema&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;In modern agentic workflows, "Memory" is replaced by an explicit &lt;strong&gt;State Schema&lt;/strong&gt;. This allows the graph to pass data between nodes with type safety.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;from typing import TypedDict, Annotated&lt;br&gt;
import operator&lt;br&gt;
from langchain_core.messages import BaseMessage

&lt;p&gt;class AgentState(TypedDict):&lt;br&gt;
  # Annotate as 'list' to append new messages instead of overwriting&lt;br&gt;
  messages: Annotated[list[BaseMessage], operator.add]&lt;br&gt;
  task_goal: str&lt;br&gt;
  generated_topology: str&lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 2: Orchestrate with LangGraph&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;We replace the legacy &lt;code&gt;Agent&lt;/code&gt; class with &lt;strong&gt;Nodes&lt;/strong&gt; and &lt;strong&gt;Edges&lt;/strong&gt;. This allows for "Time-Travel Debugging" and human-in-the-loop checkpoints.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;from langgraph.graph import StateGraph, END&lt;br&gt;
from langchain_openai import ChatOpenAI

&lt;p&gt;llm = ChatOpenAI(model="gpt-4o", temperature=0.2)&lt;/p&gt;
&lt;h1&gt;
  
  
  Define Node Logic
&lt;/h1&gt;

&lt;p&gt;def understand_task(state: AgentState):&lt;br&gt;
  # ... logic to parse natural language ...&lt;br&gt;
  return {"task_goal": "Optimized Ethylene Cracking"}&lt;/p&gt;

&lt;p&gt;def generate_topology(state: AgentState):&lt;br&gt;
  # ... logic to output process structure ...&lt;br&gt;
  return {"generated_topology": "C2H4 -&amp;gt; C2H2 + H2"}&lt;/p&gt;
&lt;h1&gt;
  
  
  Build the Graph
&lt;/h1&gt;

&lt;p&gt;workflow = StateGraph(AgentState)&lt;br&gt;
workflow.add_node("understand", understand_task)&lt;br&gt;
workflow.add_node("topology", generate_topology)&lt;/p&gt;

&lt;p&gt;workflow.set_entry_point("understand")&lt;br&gt;
workflow.add_edge("understand", "topology")&lt;br&gt;
workflow.add_edge("topology", END)&lt;/p&gt;

&lt;p&gt;app = workflow.compile()&lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Testing the Workflow&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;To run the production-grade agent, we invoke the graph with an initial state.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;result = app.invoke({"messages": ["Design an ethylene cracking process"]})&lt;br&gt;
print(result["generated_topology"])&lt;/code&gt;&lt;/pre&gt;

</description>
      <category>webdev</category>
      <category>ai</category>
      <category>tutorial</category>
      <category>discuss</category>
    </item>
    <item>
      <title>Building a Conversational AI with Claude and ChatGPT APIs: A Practical Guide</title>
      <dc:creator>Gate of AI</dc:creator>
      <pubDate>Wed, 03 Jun 2026 16:06:39 +0000</pubDate>
      <link>https://dev.to/gateofai/building-a-conversational-ai-with-claude-and-chatgpt-apis-a-practical-guide-4a3c</link>
      <guid>https://dev.to/gateofai/building-a-conversational-ai-with-claude-and-chatgpt-apis-a-practical-guide-4a3c</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;🚀 Technical Briefing:&lt;/strong&gt; This tutorial is part of our deep-dive series on Agentic Workflows at &lt;a href="https://gateofai.com" rel="noopener noreferrer"&gt;Gate of AI&lt;/a&gt;. For the full technical breakdown, interactive code sandbox, and the native Arabic translation, visit the &lt;a href="https://gateofai.com/tutorial/claude-chatgpt-api-conversational-ai-tutorial/" rel="noopener noreferrer"&gt;original article here&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;span&amp;gt;Tutorial&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;Intermediate&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;⏱ 35 min read&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;© Gate of AI 2026-06-02&amp;lt;/span&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;Architect a multi-provider LLM gateway in Next.js using App Router Route Handlers to dynamically toggle production requests between OpenAI and Anthropic architectures while maintaining state context.&lt;/p&gt;


&lt;h2&gt;Prerequisites&lt;/h2&gt;
&lt;br&gt;
  &lt;ul&gt;

    &lt;li&gt;Node.js 18.x or higher&lt;/li&gt;

    &lt;li&gt;Next.js 14.x or 15.x (App Router structure)&lt;/li&gt;

    &lt;li&gt;Valid API keys configured in the OpenAI and Anthropic developer consoles&lt;/li&gt;

    &lt;li&gt;Familiarity with polymorphic API payloads and React state composition&lt;/li&gt;

  &lt;/ul&gt;


&lt;h2&gt;What We're Building&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Production AI engineering often requires model redundancy or specialized routing—routing creative tasks to Claude and strict structural updates to GPT. In this guide, we are building a unified API abstraction layer that sanitizes, maps, and executes multi-turn conversations across both ecosystems cleanly.&lt;/p&gt;


&lt;h2&gt;Setup and Installation&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Bootstrap a clean Next.js application layer and pull down both official vendor SDK packages:&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
npx create-next-app@latest multi-provider-chat --ts --no-tailwind --app --src-dir=false&lt;br&gt;
cd multi-provider-chat&lt;br&gt;
npm install openai @anthropic-ai/sdk&lt;br&gt;
  &lt;/code&gt;&lt;/pre&gt;
&lt;br&gt;
  &lt;p&gt;Populate your local environment matrix inside &lt;code&gt;.env.local&lt;/code&gt; in your root directory:&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
OPENAI_API_KEY=your_openai_project_secret_key&lt;br&gt;
ANTHROPIC_API_KEY=your_anthropic_live_secret_key&lt;br&gt;
  &lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 1: Engineering the Unified Model Gateway&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Create your server route handler at &lt;code&gt;app/api/chat/route.js&lt;/code&gt;. We explicitly instantiate both clients and create an abstraction parser to handle the structural layout differences between OpenAI's choices array and Anthropic's content blocks.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
import { NextResponse } from 'next/server';&lt;br&gt;
import { OpenAI } from 'openai';&lt;br&gt;
import { Anthropic } from '@anthropic-ai/sdk';

&lt;p&gt;const openai = new OpenAI();&lt;br&gt;
const anthropic = new Anthropic();&lt;/p&gt;

&lt;p&gt;export async function POST(req) {&lt;br&gt;
    try {&lt;br&gt;
        const { provider, messages } = await req.json();&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;    if (!messages || !Array.isArray(messages)) {
        return NextResponse.json({ error: 'Malformed message history payload' }, { status: 400 });
    }

    let replyText = '';

    if (provider === 'openai') {
        const response = await openai.chat.completions.create({
            model: 'gpt-4o-mini',
            messages: messages.map(msg =&amp;amp;gt; ({
                role: msg.role,
                content: msg.content
            }))
        });
        replyText = response.choices[0].message.content;

    } else if (provider === 'anthropic') {
        // Anthropic separates the 'system' message from the historical array
        const systemMessage = messages.find(m =&amp;amp;gt; m.role === 'system')?.content || 'You are a precise assistant.';
        const conversationHistory = messages.filter(m =&amp;amp;gt; m.role !== 'system');

        const response = await anthropic.messages.create({
            model: 'claude-3-5-haiku-20241022',
            max_tokens: 1024,
            system: systemMessage,
            messages: conversationHistory.map(msg =&amp;amp;gt; ({
                role: msg.role === 'assistant' ? 'assistant' : 'user', // Safe role mapping
                content: msg.content
            }))
        });
        replyText = response.content[0].text;

    } else {
        return NextResponse.json({ error: 'Unsupported provider routing request' }, { status: 400 });
    }

    return NextResponse.json({ reply: replyText });

} catch (error) {
    console.error('Gateway Route Exception:', error);
    return NextResponse.json({ error: error.message || 'Internal processing error' }, { status: 500 });
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;}&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 2: Building the Polymorphic Interface Component&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Create your frontend component architecture at &lt;code&gt;app/page.js&lt;/code&gt;. We implement standard state updater functions to maintain conversational tracking history while providing an explicit drop-down to switch providers dynamically.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
'use client';&lt;br&gt;
import { useState } from 'react';

&lt;p&gt;export default function HomeChatWorkspace() {&lt;br&gt;
    const [messages, setMessages] = useState([&lt;br&gt;
        { role: 'system', content: 'You are a helpful software engineering consultant.' }&lt;br&gt;
    ]);&lt;br&gt;
    const [input, setInput] = useState('');&lt;br&gt;
    const [provider, setProvider] = useState('openai'); // Default routing value&lt;br&gt;
    const [isLoading, setIsLoading] = useState(false);&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;const handleFormSubmit = async (e) =&amp;amp;gt; {
    e.preventDefault();
    if (!input.trim() || isLoading) return;

    const incomingUserNode = { role: 'user', content: input };
    setInput('');
    setIsLoading(true);

    // Update UI state with user message immediately
    const updatedHistory = [...messages, incomingUserNode];
    setMessages(updatedHistory);

    try {
        const response = await fetch('/api/chat', {
            method: 'POST',
            headers: { 'Content-Type': 'application/json' },
            body: JSON.stringify({ provider, messages: updatedHistory })
        });

        const data = await response.json();
        if (!response.ok) throw new Error(data.error || 'Server rejected request');

        setMessages((prev) =&amp;amp;gt; [...prev, { role: 'assistant', content: data.reply }]);
    } catch (err) {
        console.error('Inference Error:', err);
        setMessages((prev) =&amp;amp;gt; [...prev, { role: 'system', content: `Error: ${err.message}` }]);
    } finally {
        setIsLoading(false);
    }
};

return (


            &amp;lt;h2&amp;gt;Multi-Model Control Panel&amp;lt;/h2&amp;gt;
             setProvider(e.target.value)} disabled={isLoading}&amp;amp;gt;
                Engine: GPT-4o-Mini
                Engine: Claude-3.5-Haiku




            {messages.filter(m =&amp;amp;gt; m.role !== 'system').map((msg, idx) =&amp;amp;gt; (

                    &amp;lt;span&amp;gt;
                        &amp;lt;strong&amp;gt;{msg.role === 'user' ? 'You' : 'AI'}:&amp;lt;/strong&amp;gt; {msg.content}
                    &amp;lt;/span&amp;gt;

            ))}



             setInput(e.target.value)} 
                placeholder="Ask a technical question..." 
                disabled={isLoading}
                style={{ flex: 1, padding: '10px', borderRadius: '4px', border: '1px solid #ccc' }}
            /&amp;amp;gt;

                {isLoading ? 'Processing...' : 'Send'}



);
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;}&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;&lt;strong&gt;⚠️ Advanced Ingestion Warning:&lt;/strong&gt; Anthropic's Messages API enforces strict array alternation. If you pass consecutive messages with the same role (e.g., &lt;code&gt;'user'&lt;/code&gt; followed by another &lt;code&gt;'user'&lt;/code&gt; node), the SDK will reject the payload with a 400 validation error. Always ensure your mapping pipeline cleanses array structure sequences before firing updates to the Claude engine.&lt;/p&gt;


&lt;h2&gt;Testing Your Routing Engine&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Boot your Next.js application workspace locally:&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;npm run dev&lt;/code&gt;&lt;/pre&gt;
&lt;br&gt;
  &lt;p&gt;Open &lt;code&gt;&lt;a href="http://localhost:3000" rel="noopener noreferrer"&gt;http://localhost:3000&lt;/a&gt;&lt;/code&gt;. Select &lt;strong&gt;GPT-4o-Mini&lt;/strong&gt; and ask a question. Then immediately switch the dropdown option to &lt;strong&gt;Claude-3.5-Haiku&lt;/strong&gt; and ask follow-up questions like &lt;em&gt;"Can you rewrite my last question in Rust?"&lt;/em&gt; Notice how the continuous context array maps safely regardless of your provider toggle swaps.&lt;/p&gt;


&lt;h2&gt;What to Build Next&lt;/h2&gt;
&lt;br&gt;
  &lt;ul&gt;

    &lt;li&gt;Convert the system to utilize streaming chunks concurrently across both components using &lt;code&gt;ReadableStream&lt;/code&gt; wrappers.&lt;/li&gt;

    &lt;li&gt;Implement automated model comparison logging to measure execution latency variations between OpenAI and Anthropic routers.&lt;/li&gt;

    &lt;li&gt;Add a fall-through logic block that automatically switches providers if one vendor encounters a 503 rate-limit error.&lt;/li&gt;

  &lt;/ul&gt;

</description>
      <category>webdev</category>
      <category>ai</category>
      <category>tutorial</category>
      <category>discuss</category>
    </item>
    <item>
      <title>How to Build Long-Running AI Agents with Google Gen AI SDK</title>
      <dc:creator>Gate of AI</dc:creator>
      <pubDate>Sun, 31 May 2026 17:42:58 +0000</pubDate>
      <link>https://dev.to/gateofai/how-to-build-long-running-ai-agents-with-google-gen-ai-sdk-419p</link>
      <guid>https://dev.to/gateofai/how-to-build-long-running-ai-agents-with-google-gen-ai-sdk-419p</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;🚀 Technical Briefing:&lt;/strong&gt; This tutorial is part of our deep-dive series on Agentic Workflows at &lt;a href="https://gateofai.com" rel="noopener noreferrer"&gt;Gate of AI&lt;/a&gt;. For the full technical breakdown, interactive code sandbox, and the native Arabic translation, visit the &lt;a href="https://gateofai.com/tutorial/build-long-running-ai-agents-gemini-python/" rel="noopener noreferrer"&gt;original article here&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;span&amp;gt;Tutorial&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;Advanced&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;⏱ 45 min read&amp;lt;/span&amp;gt;
&amp;lt;span&amp;gt;© Gate of AI 2026-05-31&amp;lt;/span&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;Step away from standard chat APIs. Learn the foundational architecture for building long-running, stateful autonomous agents inspired by the new Gemini Enterprise Unified Inbox.&lt;/p&gt;


&lt;h2&gt;Prerequisites&lt;/h2&gt;
&lt;br&gt;
  &lt;ul&gt;

    &lt;li&gt;Python 3.10 or higher&lt;/li&gt;

    &lt;li&gt;Access to the Google Gen AI SDK (Gemini 1.5 Pro or higher)&lt;/li&gt;

    &lt;li&gt;A Google Cloud Project with Billing Enabled&lt;/li&gt;

    &lt;li&gt;Advanced understanding of asynchronous Python (&lt;code&gt;asyncio&lt;/code&gt;) and state management&lt;/li&gt;

  &lt;/ul&gt;


&lt;h2&gt;What We're Building&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;With Google Cloud's announcement of Long-Running Agents in Gemini Enterprise, the development paradigm has officially shifted. In this tutorial, we will construct the foundational "pause-and-resume" architecture required to build these agents.&lt;/p&gt;
&lt;br&gt;
  &lt;p&gt;We won't just build a chatbot. We will build a stateful, asynchronous Python worker that executes a multi-step task, intentionally "pauses" when it requires simulated human approval (mimicking the Unified Inbox), and resumes upon confirmation.&lt;/p&gt;


&lt;h2&gt;Setup and Installation&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;We will use the official Google Gen AI SDK and &lt;code&gt;python-dotenv&lt;/code&gt; for our environment variables.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;pip install google-genai python-dotenv asyncio&lt;/code&gt;&lt;/pre&gt;
&lt;br&gt;
  &lt;p&gt;Secure your API credentials in a &lt;code&gt;.env&lt;/code&gt; file.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
    # .env file&lt;br&gt;
    GEMINI_API_KEY=your_gemini_api_key_here&lt;br&gt;
  &lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 1: Architecting the Stateful Client&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Unlike a standard chatbot that forgets data between queries, a long-running agent must maintain a rigid state dictionary. We initialize the official &lt;code&gt;genai.Client&lt;/code&gt; and set up our state manager.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
import os&lt;br&gt;
import asyncio&lt;br&gt;
from google import genai&lt;br&gt;
from dotenv import load_dotenv

&lt;p&gt;load_dotenv()&lt;/p&gt;

&lt;p&gt;class LongRunningAgent:&lt;br&gt;
    def &lt;strong&gt;init&lt;/strong&gt;(self):&lt;br&gt;
        # Initialize the official Google Gen AI Client&lt;br&gt;
        self.client = genai.Client(api_key=os.getenv("GEMINI_API_KEY"))&lt;br&gt;
        self.model = "gemini-1.5-pro"&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;    # This dictionary mimics the persistent state stored in a database
    self.state = {
        "status": "idle", # idle, running, awaiting_approval, completed
        "workflow_history": [],
        "pending_approval_request": None
    }

def log_action(self, action):
    print(f"[AGENT LOG]: {action}")
    self.state["workflow_history"].append(action)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 2: Building the "Pause-and-Resume" HITL Logic&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;The core innovation of Gemini's new update is the Human-in-the-Loop (HITL) Inbox. Here, we build the asynchronous logic that allows the agent to pause execution when it hits a restricted action.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
    async def request_human_approval(self, task_description):&lt;br&gt;
        """Simulates pushing a task to the Unified Inbox"""&lt;br&gt;
        self.state["status"] = "awaiting_approval"&lt;br&gt;
        self.state["pending_approval_request"] = task_description
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;    self.log_action(f"PAUSED: Awaiting human approval for: {task_description}")

    # Simulate waiting for the manager to click "Approve" in the Inbox
    while self.state["status"] == "awaiting_approval":
        await asyncio.sleep(2) # Check database/state every 2 seconds

    self.log_action("RESUMED: Human approval granted.")
    return True

def simulate_manager_approval(self):
    """External function called by your UI/Inbox when a user clicks approve"""
    if self.state["status"] == "awaiting_approval":
        self.state["status"] = "running"
        self.state["pending_approval_request"] = None
        print("\n✅ [INBOX]: Manager approved the action.\n")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;Step 3: Executing the Asynchronous Workflow&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;Now, we tie it together. We will use the &lt;code&gt;client.models.generate_content&lt;/code&gt; method to process data, but wrap it in our async execution loop.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
    async def run_multi_day_workflow(self, initial_prompt):&lt;br&gt;
        self.state["status"] = "running"&lt;br&gt;
        self.log_action("Starting long-running workflow...")
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;    # Phase 1: Autonomous Processing
    self.log_action("Analyzing request via Gemini API...")
    response = self.client.models.generate_content(
        model=self.model,
        contents=f"Analyze this task and propose a 3-step execution plan: {initial_prompt}"
    )
    self.log_action(f"Plan generated: {response.text[:100]}...")

    # Phase 2: Hitting a permission wall (Mimicking the Unified Inbox feature)
    await asyncio.sleep(1) # Simulating heavy compute time

    # The agent realizes it needs access to a restricted system (e.g., Google Drive)
    await self.request_human_approval("Access restricted Drive Folder: 'Q3 Financials'")

    # Phase 3: Post-Approval Execution
    self.log_action("Finalizing workflow with approved access...")
    final_response = self.client.models.generate_content(
        model=self.model,
        contents="The human approved access. Generate the final summary report."
    )

    self.state["status"] = "completed"
    self.log_action("Workflow Completed.")
    return final_response.text
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;p&gt;&lt;strong&gt;⚠️ Expert Tip:&lt;/strong&gt; In a production environment, do not use &lt;code&gt;asyncio.sleep&lt;/code&gt; to hold state. You must serialize the &lt;code&gt;self.state&lt;/code&gt; dictionary to a persistent database (like Redis or PostgreSQL). When the webhook from your Inbox arrives, you retrieve the state and re-initialize the agent.&lt;/p&gt;


&lt;h2&gt;Testing the Unified Inbox Architecture&lt;/h2&gt;
&lt;br&gt;
  &lt;p&gt;To run this, we will use Python's &lt;code&gt;asyncio.gather&lt;/code&gt; to run the agent in the background while simulating a human checking their inbox.&lt;/p&gt;
&lt;br&gt;
  &lt;pre&gt;&lt;code&gt;&lt;br&gt;
async def main():&lt;br&gt;
    agent = LongRunningAgent()
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# Start the agent as a background task
agent_task = asyncio.create_task(
    agent.run_multi_day_workflow("Audit the Q3 Marketing Spend")
)

# Simulate the human manager checking their inbox after 5 seconds
await asyncio.sleep(5)
agent.simulate_manager_approval()

# Wait for the agent to finish
result = await agent_task
print(f"\n[FINAL OUTPUT]:\n{result}")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;if &lt;strong&gt;name&lt;/strong&gt; == '&lt;strong&gt;main&lt;/strong&gt;':&lt;br&gt;
    asyncio.run(main())&lt;br&gt;
  &lt;/p&gt;&lt;/code&gt;&lt;/pre&gt;


&lt;h2&gt;What to Build Next&lt;/h2&gt;
&lt;br&gt;
  &lt;ul&gt;

    &lt;li&gt;Replace the simulated wait loop by saving the agent's state to a PostgreSQL database.&lt;/li&gt;

    &lt;li&gt;Build a frontend React/Next.js "Unified Inbox" UI that triggers the webhook to resume the agent.&lt;/li&gt;

    &lt;li&gt;Implement the official &lt;code&gt;genai.types.Tool&lt;/code&gt; configurations to let the agent actually execute the actions post-approval.&lt;/li&gt;

  &lt;/ul&gt;

</description>
      <category>webdev</category>
      <category>ai</category>
      <category>tutorial</category>
      <category>discuss</category>
    </item>
    <item>
      <title>Building a Chatbot with Mistral's Mixtral API: A Step-by-Step Guide</title>
      <dc:creator>Gate of AI</dc:creator>
      <pubDate>Sat, 23 May 2026 07:54:16 +0000</pubDate>
      <link>https://dev.to/gateofai/building-a-chatbot-with-mistrals-mixtral-api-a-step-by-step-guide-3fdj</link>
      <guid>https://dev.to/gateofai/building-a-chatbot-with-mistrals-mixtral-api-a-step-by-step-guide-3fdj</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;🚀 Technical Briefing:&lt;/strong&gt; This tutorial is part of our deep-dive series on Agentic Workflows at &lt;a href="https://gateofai.com" rel="noopener noreferrer"&gt;Gate of AI&lt;/a&gt;. For the full technical breakdown, interactive code sandbox, and the native Arabic translation, visit the &lt;a href="https://gateofai.com/tutorial/mistral-mixtral-api-chatbot-tutorial/" rel="noopener noreferrer"&gt;original article here&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Tutorial&lt;br&gt;
    Intermediate&lt;br&gt;
    ⏱ 30 min read&lt;br&gt;
    © Gate of AI 2026-05-23&lt;/p&gt;

&lt;p&gt;Learn to harness the power of the official Mistral AI API to create a responsive, intelligent chatbot capable of handling complex queries with ease.&lt;/p&gt;

&lt;p&gt;Prerequisites&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Python 3.8 or higher
Access to Mistral AI API (API key required from console.mistral.ai)
Intermediate understanding of Python programming
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;What We're Building&lt;br&gt;
  In this tutorial, you will learn how to build a sophisticated chatbot using the official Mistral AI Python SDK. This chatbot will process natural language queries, provide coherent responses, and handle conversational topics by leveraging Mistral's latest models.&lt;br&gt;
  The finished project will be a command-line application that interacts with users, processes conversational intents, and showcases the capabilities of modern AI-driven agents.&lt;/p&gt;

&lt;p&gt;Setup and Installation&lt;br&gt;
  To start, install the official Mistral SDK and &lt;code&gt;python-dotenv&lt;/code&gt; for secure configuration.&lt;br&gt;
  pip install mistralai python-dotenv&lt;br&gt;
  Store your API key in a &lt;code&gt;.env&lt;/code&gt; file to ensure it is not hardcoded.&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# .env file
MISTRAL_API_KEY=your_api_key_here
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;Step 1: Setting Up the API Client&lt;br&gt;
  We will use the &lt;code&gt;Mistral&lt;/code&gt; client class from the official SDK, which is the recommended way to interact with Mistral's endpoints.&lt;/p&gt;

&lt;p&gt;import os&lt;br&gt;
from mistralai import Mistral&lt;br&gt;
from dotenv import load_dotenv&lt;/p&gt;

&lt;p&gt;load_dotenv()&lt;/p&gt;

&lt;p&gt;class ChatbotClient:&lt;br&gt;
    def &lt;strong&gt;init&lt;/strong&gt;(self):&lt;br&gt;
        # Client automatically reads MISTRAL_API_KEY from environment variables&lt;br&gt;
        self.client = Mistral(api_key=os.getenv("MISTRAL_API_KEY"))&lt;br&gt;
        self.model = "mistral-small-latest"&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;def send_query(self, query):
    response = self.client.chat.complete(
        model=self.model,
        messages=[{"role": "user", "content": query}]
    )
    return response.choices[0].message.content
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;Step 2: Building the Chatbot Interface&lt;br&gt;
  This command-line interface allows for continuous interaction with the model.&lt;/p&gt;

&lt;p&gt;def main():&lt;br&gt;
    client = ChatbotClient()&lt;br&gt;
    print("Welcome to the Mistral Chatbot! Type 'exit' to quit.")&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;while True:
    user_input = input("You: ")
    if user_input.lower() == 'exit':
        print("Goodbye!")
        break

    try:
        response = client.send_query(user_input)
        print(f"Bot: {response}")
    except Exception as e:
        print(f"Error: {e}")
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;if &lt;strong&gt;name&lt;/strong&gt; == '&lt;strong&gt;main&lt;/strong&gt;':&lt;br&gt;
    main()&lt;/p&gt;

&lt;p&gt;Step 3: Enhancing with Contextual Awareness&lt;br&gt;
  To enable multi-turn conversations, you must maintain a list of messages that includes the conversation history.&lt;/p&gt;

&lt;p&gt;class EnhancedChatbotClient(ChatbotClient):&lt;br&gt;
    def &lt;strong&gt;init&lt;/strong&gt;(self):&lt;br&gt;
        super().&lt;strong&gt;init&lt;/strong&gt;()&lt;br&gt;
        self.history = [{"role": "system", "content": "You are a helpful assistant."}]&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;def send_query_with_context(self, query):
    self.history.append({"role": "user", "content": query})

    response = self.client.chat.complete(
        model=self.model,
        messages=self.history
    )

    answer = response.choices[0].message.content
    self.history.append({"role": "assistant", "content": answer})
    return answer
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;⚠️ Expert Tip: Always use the official SDK's message structure. Properly defining roles ("system", "user", "assistant") is critical for maintaining coherent context.&lt;/p&gt;

&lt;p&gt;Testing Your Implementation&lt;br&gt;
  Run your script and interact with the chatbot to verify the contextual memory.&lt;/p&gt;

&lt;h1&gt;
  
  
  Run the script
&lt;/h1&gt;

&lt;p&gt;python chatbot.py&lt;/p&gt;

&lt;p&gt;What to Build Next&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Integrate the chatbot into a web application using Flask or Django.
Implement streaming responses using client.chat.stream() for a real-time typing effect.
Experiment with mistral-medium-latest or mistral-large-latest for more complex reasoning tasks.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

</description>
      <category>python</category>
      <category>ai</category>
      <category>webdev</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>Reverse Engineering X’s Recommendation Algorithm: Programmatic Hooks for Tech Creators</title>
      <dc:creator>Gate of AI</dc:creator>
      <pubDate>Fri, 22 May 2026 23:43:26 +0000</pubDate>
      <link>https://dev.to/gateofai/reverse-engineering-xs-recommendation-algorithm-programmatic-hooks-for-tech-creators-2g1h</link>
      <guid>https://dev.to/gateofai/reverse-engineering-xs-recommendation-algorithm-programmatic-hooks-for-tech-creators-2g1h</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;🚀 Technical Briefing:&lt;/strong&gt; This tutorial is part of our deep-dive series on Agentic Workflows at &lt;a href="https://gateofai.com" rel="noopener noreferrer"&gt;Gate of AI&lt;/a&gt;. For the full technical breakdown, interactive code sandbox, and the native Arabic translation, visit the &lt;a href="https://gateofai.com/tutorial/reverse-engineering-x-algorithm-programmatic-hooks/" rel="noopener noreferrer"&gt;original article here&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Tutorial&lt;br&gt;
Intermediate&lt;br&gt;
⏱ 8 min read&lt;br&gt;
© Gate of AI&lt;br&gt;
Reverse engineer the open-sourced X recommendation algorithm to write high-converting hooks and maximize your content's organic reach.&lt;/p&gt;

&lt;p&gt;The Content Ecosystem Strategy&lt;br&gt;
To build a sustainable content architecture, your website should always be the ultimate source of truth, while social platforms like YouTube and X serve as marketing funnels. This tutorial breaks down the technical secrets of the X algorithm so you can drive massive traffic back to your core platforms.&lt;/p&gt;

&lt;p&gt;Reverse Engineering the X Algorithm&lt;br&gt;
Following the recent open-source release of the X "For You" feed algorithm, developers and content creators finally have programmatic proof of what actually drives engagement. It is no longer just about likes and retweets; the core of the ranking system relies on behavioral metrics that track exactly how users interact with your text on screen.&lt;br&gt;
In this guide, we will analyze the exact parameters found in the xAI repository to understand how to craft the perfect "Hook" and guarantee maximum visibility.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;The Technical Secret: The "Dwell Time" Parameter&lt;br&gt;
Deep within the open-source code, there is a massive weighting applied to a metric known as Dwell Time. The X algorithm actively tracks the exact amount of time a user spends reading your tweet before they scroll past it.&lt;br&gt;
If your post causes a user to pause their scrolling, the algorithm immediately flags your content as "high-value." The longer they stay on the text, the higher your algorithmic score spikes. This means your primary goal as a writer is not just to deliver information, but to visually and psychologically stop the scroll within the first two seconds.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;The Formula for a Programmatic Hook&lt;br&gt;
Based on the code's preference for high Dwell Time, standard introductions fail because they are easily skimmable. To force the algorithm to rank your tweet higher, your hook must create instant cognitive friction.&lt;br&gt;
The most effective hooks utilize two specific triggers:&lt;/p&gt;

&lt;p&gt;The Shocking Question: Frame your opening as a question that challenges an industry standard. (e.g., "Is the era of proprietary AI models completely dead?")&lt;br&gt;
The Terrifying Metric: Start with an alarming or massive data point that forces the brain to process the number. (e.g., "90% of developers are using outdated attention mechanisms. Here is why.")&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;These structures force the reader to pause and process the information, directly feeding the Dwell Time parameter the data it needs to boost your post.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;The "Show More" Bonus Multiplier&lt;br&gt;
One of the most actionable discoveries in the codebase is the Bonus Boost awarded for explicit interaction. While likes and bookmarks are valuable, the algorithm highly rewards content that prompts the user to click the "Show More" text expansion button.&lt;br&gt;
From a programmatic standpoint, clicking "Show More" is registered as an explicit, high-intent positive engagement. To leverage this:&lt;/p&gt;

&lt;p&gt;Format your tweets to be intentionally long enough to trigger the truncation limit.&lt;br&gt;
Place your most compelling hook or a cliffhanger exactly where the text cuts off, making the user physically click to read the rest of the tutorial or find the link to your site.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;// Conceptual representation of X's HeavyRanker feature scoring&lt;/p&gt;

&lt;p&gt;function calculateTweetScore(tweet) {&lt;br&gt;
    let baseScore = tweet.likes * 0.5 + tweet.retweets * 1.0;&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// The Dwell Time Multiplier (Logarithmic scaling)
if (tweet.dwellTimeSeconds &amp;amp;gt; 2) {
    baseScore += Math.log(tweet.dwellTimeSeconds) * 2.5;
}

// Explicit Intent Action: The "Show More" Expansion
if (tweet.isTextExpanded) {
    baseScore *= 1.4; // 40% algorithmic boost multiplier
}

return baseScore;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;

&lt;p&gt;}&lt;/p&gt;

&lt;p&gt;🧠 Architecture Mindset: Do not just give all the value away on the timeline. Use the "Show More" technique to tease a deeper technical secret, and place the link to your full Gate of AI article in the subsequent thread.&lt;/p&gt;

&lt;p&gt;Have a question about this tutorial?&lt;br&gt;
Our AI assistant has read this tutorial and is ready to answer all your questions instantly. Open the chat for step-by-step guidance!&lt;/p&gt;

</description>
      <category>python</category>
      <category>ai</category>
      <category>gemini</category>
      <category>openai</category>
    </item>
    <item>
      <title>Stop Relying on One LLM: Build a Dual-Engine Agent with GPT-4o &amp; Gemini</title>
      <dc:creator>Gate of AI</dc:creator>
      <pubDate>Fri, 22 May 2026 23:23:36 +0000</pubDate>
      <link>https://dev.to/gateofai/stop-relying-on-one-llm-build-a-dual-engine-agent-with-gpt-4o-gemini-2pgi</link>
      <guid>https://dev.to/gateofai/stop-relying-on-one-llm-build-a-dual-engine-agent-with-gpt-4o-gemini-2pgi</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;🚀 Technical Briefing:&lt;/strong&gt; This tutorial is part of our deep-dive series on Agentic Workflows at &lt;a href="https://gateofai.com" rel="noopener noreferrer"&gt;Gate of AI&lt;/a&gt;. For the full technical breakdown, interactive code sandbox, and the native Arabic translation, visit the &lt;a href="https://gateofai.com/tutorial/building-dual-engine-ai-agent-openai-gemini-tutorial/" rel="noopener noreferrer"&gt;original article here&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;

</description>
      <category>python</category>
      <category>ai</category>
      <category>gemini</category>
      <category>openai</category>
    </item>
  </channel>
</rss>
