AI fixed how fast I can build. It broke how I know what I’m building.

A markdown convention I wrote to track 5-10 half-built projects without losing my mind, and without another SaaS subscription.

TL;DR. AI made it cheap to generate ideas, draft plans, and start projects. It did not make it cheap to track them. I ended up with 5-10 half-built projects, plan files everywhere, no idea which were stalled vs. blocked vs. abandoned, and no way to explain status to stakeholders or even to future-me. I tried Jira, Linear, Notion, none stuck. I wrote a markdown convention for myself instead: 3 directories, 7-field frontmatter, one HTML dashboard. AI coding assistants (Claude Code, Cursor, Antigravity, Windsurf) read it natively as a side effect. Repo at the bottom.

The new bottleneck

For most of my career, the bottleneck was writing the code. Planning was the easy part. You’d think a feature through, scope it, then spend the next two weeks actually building it.

AI inverted this. I can now scope a feature with Claude in 20 minutes and have a working prototype in an afternoon. That’s genuinely transformative. But the bottleneck didn’t disappear, it moved.

The new bottleneck is knowing what I’m actually working on.

I have 5-10 half-built projects right now. Some I started with AI and never finished. Some I planned with AI and never started. Some are blocked on something I forgot. Some are stalled because I lost interest two weeks in. Some have dependencies on other half-built things, and the dependencies aren’t visible anywhere.

If you asked me “what are you actively building this week?”, I genuinely couldn’t tell you without opening five repos and reading scattered markdown files. That’s the real productivity problem AI introduced, and it’s the one no tool I tried actually solves.

What the mess looks like in practice

Concretely, in any given month, I’ll have:

  • 2-3 active plans I’m working on right now
  • 1-2 stalled plans I started enthusiastically and quietly abandoned around the 60% mark
  • 2-3 ideas I asked AI to plan out that never moved past the planning doc
  • A few “I should pick this up again” thoughts about half-built things from 2 months ago
  • Dependencies between some of these that I knew when I wrote them and have since forgotten

Every one of those generates a FEATURE_X_PLAN.md somewhere. At one point I had 38 plan files at the root of one repo, none of which I could quickly classify as “alive” or “dead” without re-reading them.

The result: when someone (a stakeholder, or future-me opening the repo cold after weeks away) asked me what state things were in, I couldn’t answer. Not “I gave a vague answer”, I genuinely could not produce a clear answer without an hour of archaeological work.

What I’d tried

Jira. Worked for a week. Opening a browser tab and clicking through fields became higher friction than writing one more markdown file in the editor.

Linear. Same outcome, faster. Better UX doesn’t matter if the friction is “leave my editor”.

Notion. Lasted longer because it felt closer to writing. Sat unused after three weeks anyway. Became a third source of state, not a single source.

Pattern I missed for too long: these tools are built for teams shipping a small number of larger things in a coordinated way. That’s not what AI-assisted solo work looks like. AI-assisted work generates a larger number of smaller, parallel, shifting things with unclear states and frequent context switches. Different shape of work needs a different shape of tracking.
Forcing AI-velocity work into team-throughput tools is the wrong fit, and the friction is the symptom.

What I built instead

A convention, not a tool. Lives entirely in the repo as plain text.

Three directories:

plans/
  active/      <- what's being built right now
  shipped/     <- what's done (don't delete, keep the receipts)
  superseded/  <- what got abandoned (don't delete, keep the why)

The “don’t delete” part matters. Old plans are evidence of how a project actually evolved. Deleting them erases the history of decisions.

One file per feature, with 7 fields of frontmatter:

---
status: active
priority: P1
owner: yasiru
type: feature
depends_on: []
blocks: []
last_updated: 2026-05-17
---

The depends_on and blocks fields are the ones that quietly do the most work. Plans aren’t independent; they have a dependency graph, and the graph is what lets me see “I can’t start B until A ships.”

One STATUS.md at plans/STATUS.md that answers “where are we right now” in one place. In flight, up next, recently shipped, backlog. I open this in the morning instead of trying to remember.

One HTML dashboard (roadmap.html) that reads the auto-generated plans.json and renders an interactive Gantt + dependency graph + filterable cards. Static file, no server, no account, no login. This is the thing I send to stakeholders. They open a URL, they see what’s happening. No tool training, no permissions, no monthly seat cost. Just a webpage.

The whole convention is about 300 lines of code and lives in your repo. No service, no build step.

The AI part wasn’t the goal, but it ended up mattering

I built this for me. The primary audience is the human (often future-me) trying to remember what state 8 different projects are in.

But because the format is plain markdown with predictable structure, AI coding assistants read it natively. No integration, no MCP server, no plugin. Claude Code, Cursor, Antigravity, Windsurf, all of them just open the files and know what’s in flight.

When I start a Claude session now, it reads STATUS.md and the relevant plan files. It already knows the state. We start working in two messages instead of fifteen.

That wasn’t the goal. It’s a consequence of writing things down clearly.

The insight that made it click: AI didn’t fix my planning problem. AI made my planning problem urgent. The fix was structure I should have had all along.

What actually changed

Three things, in order of unexpected impact.

One: I can answer “what are you building this week” in 10 seconds. I open STATUS.md. The answer is there. I didn’t realise how much cognitive load I was carrying around not being able to answer that question instantly.

Two: stakeholders and future-me can see the dashboard. When someone asks about a project’s status, I send the roadmap.html link. When future-me opens a side project I haven’t touched in two months, the dashboard tells me where I left off without an archaeological dig. The dashboard is a static page, no login, works on phone. Status updates went from “I owe you a write-up” to “here’s the link, click around.”

Three: AI sessions stopped opening with 15 minutes of context. Side effect, but a big one. The AI now knows what I shipped last week without me re-explaining.

The 5-10 half-built projects didn’t go away. I still have them. But now I can see them, classify them, and consciously decide what to do with each one. Some moved to superseded/ (honest “I’m not finishing this”). Some moved to a “later” status with a reason. Some got picked up again because seeing them on the dashboard reminded me I cared.

The mess didn’t vanish; it became legible.

Where this fits in the wider trend

AI-assisted development is shifting toward spec-driven workflows. The spec, the plan, the structured intent becomes a first-class artifact that your AI assistant reads and writes against, not just a doc you wrote once and forgot.

GitHub’s Spec Kit (released late 2025) handles the per-feature spec workflow really well: define one feature, generate its spec, generate the plan, generate the tasks, execute. It’s good.

Plans is the portfolio layer for the same shift. Spec Kit answers “how do I build this one feature well”. Plans answers “what are the 8 features I’m juggling, which are alive, which are dead, which are blocked, and what’s the next thing I should pick up”. Different layer of the same trend.

If you’re already doing spec-driven work with Spec Kit (or anything similar), Plans is the thing that keeps the multi-feature view legible. If you’re not yet doing spec-driven work, Plans is a low-cost way to start, because the convention itself nudges you in that direction.

Why I’m sharing this now

Two reasons.

One: I’m genuinely curious whether this is a me-problem or a universal one. If you’re a solo dev or small team using AI coding assistants, do you also have 5-10 half-built things you can’t track? How are you managing it? I want to know if I built something useful only to me, or if this is a real shared pain that nobody’s solved.

Two: the convention is MIT and the repo is public. If it sounds useful, the install is one curl one-liner. If it doesn’t fit your workflow, that’s also useful signal for me.

Where to find it

Repo, docs, live dashboard demo, and install instructions: github.com/yrangana/Plans

If you try it, I’d love to know what works and what breaks. If you don’t try it but the problem resonates, I’d love to know how you’ve solved it yourself. Either way, drop a comment, that’s the signal I’m actually trying to gather.

Built this as a personal tool, sharing it as a convention. No business model, no roadmap pressure, just markdown files and one HTML dashboard. If a bigger player (GitHub, Anthropic, etc.) ships something better in 6 months, I’ll happily migrate. Until then, this is what I use.

AICoding #DeveloperTools #SoftwareEngineering #ProductivityTools #IndieDev #SoloFounder

Debugging DNS leaks: why your VPN isn’t hiding what you think it is

Last month I was setting up a hardened dev environment for a client doing security research. They wanted all traffic from their workstation tunneled through a VPN, no exceptions. Simple, right? Install WireGuard, flip the toggle, done.

Then I ran a leak test and watched their real ISP-assigned DNS server pop up on the report. The traffic was tunneled. The DNS queries weren’t. We’d been working under a false sense of privacy for a week.

This is one of those bugs that doesn’t crash anything, doesn’t throw an error, and silently undermines the entire reason you set up the VPN in the first place. Let’s walk through what’s actually happening and how to fix it for good.

The frustrating problem

You’ve done everything right. You’re connected to a VPN. curl ifconfig.me returns the VPN’s exit IP. Your routing table looks clean. And yet, when you visit a DNS leak test site, your ISP’s resolver shows up in the results.

Worse: in some cases your VPN tunnel is fine for HTTP and HTTPS, but DNS is going out of band. Every domain you visit is still visible to your ISP, your coffee shop’s network, or whoever else is between you and the resolver you didn’t mean to use.

If you’re running this setup on a fleet of dev boxes or CI runners that talk to internal services, the consequences get worse. Internal hostnames can leak to public resolvers. Hostnames are often as sensitive as the queries themselves.

Root cause: DNS is not part of your VPN tunnel by default

Here’s the thing most VPN tutorials gloss over. A VPN tunnel routes IP packets. DNS resolution happens at the OS level, often before the packet routing decision, using whatever resolver was configured by your DHCP lease, your /etc/resolv.conf, or your systemd-resolved stub.

There are usually three culprits:

  • systemd-resolved keeps per-link DNS configurations and may continue using the original interface’s DNS even when traffic is routed elsewhere.
  • Browsers with DNS-over-HTTPS (Firefox, Chrome) bypass the OS resolver entirely and talk directly to a hardcoded DoH endpoint over HTTPS — which is tunneled through the VPN, but goes to a third party you may not trust.
  • Applications using their own resolvers — Go binaries with GODEBUG=netdns=go, some container runtimes, and language-specific resolver libraries can ignore system settings.

The VPN sees the encrypted DoH request and dutifully tunnels it. The OS resolver sends its plaintext UDP/53 query out the wrong interface. Both paths can coexist on the same machine, which is what makes this so confusing to debug.

Step 1: Confirm the leak

Before fixing anything, prove it’s actually leaking. The cheapest reliable test is tcpdump on the physical interface (not the VPN interface) while you trigger a lookup.

# In one terminal, watch DNS on your physical NIC
sudo tcpdump -i wlan0 -n 'udp port 53 or tcp port 53'

# In another terminal, trigger a fresh lookup
# Use a unique domain so cached answers don't hide the issue
dig $(uuidgen | tr A-Z a-z).example.com

If anything shows up on the first terminal, you’re leaking. If the only DNS traffic appears on your VPN interface (wg0, tun0, etc.), you’re clean.

You can also check what resolver your system thinks it’s using:

# systemd-resolved status, per-interface
resolvectl status

# Classic view
cat /etc/resolv.conf

# What's actually being asked, in real time
sudo resolvectl monitor

The monitor subcommand is underrated — it shows every query the stub resolver processes, including which interface it was sent over.

Step 2: Force DNS through the tunnel

The fix depends on your VPN client, but the principle is the same: every DNS query must travel inside the encrypted tunnel and hit a resolver on the other side.

For a WireGuard config, this is one line:

[Interface]
PrivateKey = <your-private-key>
Address = 10.0.0.2/24
# Use a resolver that lives on the VPN side
DNS = 10.0.0.1

[Peer]
PublicKey = <peer-public-key>
Endpoint = vpn.example.com:51820
# Route everything, including DNS
AllowedIPs = 0.0.0.0/0, ::/0

The DNS = line tells wg-quick to update /etc/resolv.conf (or talk to systemd-resolved) so queries go to a server reachable only through the tunnel. The AllowedIPs = 0.0.0.0/0 part ensures the packet to that resolver actually enters the tunnel — without it, your route table might still send the DNS query out the default gateway.

For OpenVPN, the equivalent push options usually come from the server side, but you can force them locally:

# In your client config
dhcp-option DNS 10.8.0.1
block-outside-dns       # Windows-only, blocks leaks aggressively
script-security 2
up /etc/openvpn/update-resolv-conf
down /etc/openvpn/update-resolv-conf

On macOS and Linux, that update-resolv-conf script is the one that actually modifies the system resolver. It’s worth reading — it’s a useful template for understanding how DNS gets injected at runtime.

Step 3: Tame the browsers and runtimes

This is the step most people skip. Even with a perfect VPN config, Firefox and Chrome can still bypass your OS resolver if DoH is enabled.

For Firefox, set this in about:config:

network.trr.mode = 5   // Off by user choice; do not use DoH

Mode 5 disables DoH entirely. If you want DoH but routed through your VPN’s resolver, use mode 3 and set network.trr.uri to your tunnel-side endpoint. The Mozilla TRR docs explain the modes in detail.

For Go programs, force the system resolver:

// Force cgo-based resolution which respects /etc/resolv.conf changes
// done by the VPN client. The pure-Go resolver has caching that
// can outlast a VPN session change.
import _ "net"

// Or via environment
// GODEBUG=netdns=cgo+2

The +2 gives you debug output showing which resolver path was actually taken — invaluable when you’re not sure if your fix landed.

Step 4: Block the leak path entirely

Belt and suspenders. Add firewall rules that drop any DNS traffic not going through the tunnel. This way, if a misconfigured app tries to bypass, it fails loudly instead of leaking silently.

# nftables: block UDP/53 and TCP/53 on the physical interface
sudo nft add table inet vpn_guard
sudo nft add chain inet vpn_guard output { type filter hook output priority 0 ; }
sudo nft add rule inet vpn_guard output oifname wlan0 udp dport 53 drop
sudo nft add rule inet vpn_guard output oifname wlan0 tcp dport 53 drop

If an app tries to leak, it gets a connection refused instead of a successful query to your ISP. That’s a much better failure mode — you’ll notice it immediately.

Prevention tips for future projects

  • Test the leak path every time you change network config. Don’t trust that the previous setup still works after a kernel update or VPN client upgrade.
  • Prefer kill-switch behavior — drop all non-VPN traffic at the firewall when the tunnel is down. Most modern VPN clients support this; if yours doesn’t, use nftables.
  • Standardize DNS at the tunnel exit. Run an unbound or dnsmasq instance on the VPN server so you control the resolver path end to end.
  • Audit application-layer resolvers. Browsers, container runtimes, and language standard libraries each have their own DNS quirks. Document them per project.
  • Run a periodic automated leak test. A daily cron job that runs dig against a unique subdomain and checks your authoritative server’s logs for the source IP works well.

DNS leaks are the kind of bug that hides in plain sight. The fix isn’t hard once you know where to look, but the surface area is bigger than most people realize. If you’re going to put the work into setting up a VPN, spend the extra hour making sure your name resolution actually respects it.

Build a Socratic Study Buddy with Gemma 4: A Beginner’s Guide to Running AI Locally

The landscape of AI has shifted from “bigger is better” to “smarter is better.” We are entering the era of intelligence-per-parameter—a metric of how much reasoning power is packed into a compact model. Gemma 4, built on the latest research from Google DeepMind, brings high-level, multi-step reasoning directly to your own hardware.

This guide will show you how to build a Socratic Study Buddy—a tutor that doesn’t just give you answers but helps you think through problems—while keeping your data 100% private using a custom local web interface.

What I Built

I built a local Socratic Study Buddy application. It pairs the localized inference engine of LM Studio with a custom-built Streamlit Web UI frontend. Instead of acting as a lazy “answer engine” that does a student’s homework for them, this tool forces the underlying Gemma 4 model to plan pedagogical strategies and use structured dialogue to guide critical thinking.

Why Gemma 4 Matters for Learning

Gemma 4 is a “Thinking Model.” Older AI models functioned like advanced autocomplete, predicting the next word based on patterns. Gemma 4 has the capacity for a native Chain-of-Reasoning process.

Instead of jumping straight to an answer, Gemma 4 works through logical steps internally before it speaks. This makes it a perfect mentor. While other models might just do your homework, Gemma 4 is trained to identify where you are stuck and nudge you toward the solution.

Choosing Your Brain: The Official Model Sizes

To run this locally, you need to pick the right “size” for your computer. Gemma 4 comes in four official variants:

  • Effective 2B (E2B): Tiny and lightning-fast. Optimized for high-end phones or older laptops with 4GB–8GB of RAM.

  • Effective 4B (E4B): The “Sweet Spot” for most modern laptops with 8GB–12GB of RAM. This is the entry point for high-quality image and audio understanding.

  • 26B A4B (Mixture-of-Experts): The speed demon. It has 26 billion parameters but only uses 4 billion at a time to answer. You get high-quality reasoning with fast speeds. Requires 16GB–24GB of RAM.

  • 31B Dense: The flagship. This is the smartest model in the family, providing maximum reasoning quality for complex math. Use this if you have a powerful workstation with 32GB+ of RAM.

Setup: Bringing the Brain to Your Frontend

Instead of staying restricted to standard desktop setups, we bridge the model into a lightweight web dashboard.

Step 1. Weight Retrieval & Backend Hosting

1. Search for Gemma 4: Open LM Studio and click the Magnifying Glass. Type "Gemma 4".

2. Select a GGUF: Look for files labeled GGUF (a compressed file format that lets heavy models run on consumer hardware).

3. Choose Your Quantization: Look for Q4_K_M (a version that balances intelligence with low memory usage).

4. Start the Local Server:: Head to the Local Server tab in LM Studio, load your downloaded model, ensure your system prompts are injected, and start the service on port 1234. Turn GPU Offload to “Max” to leverage your graphics card.

Step 2. Running the Custom Web UI

To spin up the clean web chat interface shown below, clone the repository, install the dependencies, and launch the frontend file:

pip install streamlit openai
streamlit run app.py

Demo

Here is how the complete architecture interacts within the custom Python frontend workspace:

The UI Environment Overview

The implementation splits backend configuration details directly away from the active learning space, allowing seamless swaps between running models:

The Project: The Socratic Study Buddy Prompt

In your local configuration workspace or the core application prompt files, we pass this instruction using the official <|think|> control token sequence to isolate the reasoning channel:

<|think|>
You are an expert academic tutor. You are forbidden from giving the final answer. Instead, use your internal reasoning to identify the core concept the student is struggling with and ask guiding questions.

The “Thinking” Advantage in Action

When you ask the web component: “I don’t understand how recursion works in coding.”

Gemma 4 enters its Internal Thought Channel. Within your local terminal execution or dashboard view, you will see it process its strategy before printing its output:

Gemma 4 (Internal Reasoning): The user wants to know recursion. Giving code directly violates the Socratic constraint. I will use a structural stack analogy, like a line of people or nesting boxes, to force them to identify the concept of a terminating condition.

Tutor Output Response:

“To understand recursion, we first need to understand a ‘base case.’ If you were standing in a line of people, how would you know your position without counting everyone yourself?”

Beyond Chat: Real-World Visuals

One of the best ways to study is to visualize logic. You can ask your Study Buddy to "Draw the logic of this concept." It will generate clean Mermaid.js code directly in the conversation panel:

User: “Show me the logic of the Socratic method we just used.”
Gemma 4: “Here is the flowchart of our session:”

graph TD
    A[Student Asks Question] --> B{Model Thinks}
    B --> C[Identify Missing Concept]
    C --> D[Ask Guiding Question]
    D --> E[Student Responds]
    E -->|Correct| F[Nudge to Next Step]
    E -->|Incorrect| G[Simplify Analogy]

Code

The entire layout—including the Python automation scripts, system prompt templates, configurations, and the Streamlit frontend architecture—is completely open-source:
👉 Check out the GitHub Repository Here

Digital Sovereignty & Ethical AI Safety

Building with open-source models like Gemma 4 is a foundational ethical choice:

  • Privacy (Digital Sovereignty): Every question you ask stays on your machine. Your learning struggles aren’t being used to train a corporate model.

  • The Trade-off: Unlike cloud models, a local model is your responsibility. You must verify its facts, as it doesn’t have an external “safety filter” monitoring the conversation.

Advantages:

  • Transparency: You can inspect the weights and the “thinking” process, which is impossible with closed-source models.

  • Privacy: Since it runs locally in LM Studio or on your private GKE cluster, your data never leaves your environment.

Disadvantages:

  • Resource Intensity: High-reasoning models still require significant compute power compared to lightweight “dumb” bots.

  • Guardrail Responsibility: Unlike a managed API that filters every word, an open-source model places the “Safety Filter” responsibility on you. You must implement your own output classifiers to ensure the model stays within educational boundaries.

Conclusion

You’ve gone from raw local model files to running a custom, world-class educational reasoning platform directly on your laptop. You’ve built an app that doesn’t just echo stored training text—it actively fosters critical thinking.

Your Challenge: Use your newly built Web UI Study Buddy to tackle a topic you’ve always found intimidating—maybe organic chemistry or financial engineering. How does having an interface powered by a “Thinking Model” change the way you interact with complex documentation?

Next Steps: Ready to scale from a chat interface to fully autonomous pipelines? Check out the Pi Coding Agent by Patrick Loeber—a minimal terminal client that bridges local Gemma 4 instances straight to your terminal environment so it can write, debug, and run code directly for you!

Engineering RAG Systems That Actually Work: Conversational Retrieval, Page Awareness & Debugging (Part 5)

Final Rag Architecture

Final Rag Architecture

From a working prototype to something that actually behaves like a real system.

Introduction

In the previous parts, we built a fairly solid RAG pipeline:

  • Vector search using FAISS
  • Better chunking strategies
  • Context optimization
  • HyDE for improving retrieval quality

At that point, the system worked. It could answer questions from a document.

But it still didn’t feel right.

If you’ve used systems like ChatGPT, you know the difference immediately. The answers are not just correct — they are contextual, conversational, and consistent across turns.

Our RAG system wasn’t there yet.

What was still missing?

A few practical issues started showing up:

  • Follow-up questions like “explain more” didn’t work well
  • Queries without enough context failed silently
  • Retrieval sometimes returned semantically similar but irrelevant chunks
  • There was no clear way to debug why something went wrong

This part focuses on solving exactly those problems.

Goal for this part

Move from:

Query → Retrieve → Answer

To something closer to:

Understand → Retrieve → Validate → Answer → Debug

1. Conversational Retrieval

A basic RAG pipeline treats every query independently. That works for demos, but not for real usage.

Users don’t ask perfectly structured questions every time. They ask things like:

  • “Explain this”
  • “Continue”
  • “What does that mean?”

Without context, these queries are meaningless.

Making queries context-aware

Instead of using only the current query, we include recent conversation history.

You’re already doing this in two places.

HyDE (used with context)

def generate_hypothetical_answer(query, chat_history):
    recent_user = [m["content"] for m in chat_history[-4:] if m["role"] == "user"]
    history_text = " | ".join(recent_user[-2:])

    prompt = (f"Write a 2-sentence technical summary answering: {query}n"
              f"Recent user context: {history_text}")

    response = ollama.generate(model=HYDE_MODEL, prompt=prompt, stream=False)
    return response['response']

This makes the generated “hypothetical answer” more aligned with the conversation, not just the current query.

Passing conversation into the final answer

history_text = "n".join([
    f"{history['role']}: {history['content']}"
    for history in chat_history[-5:]
])

This allows the model to generate responses that are consistent across turns.

Result

  • Queries become less brittle
  • Retrieval improves for vague inputs
  • Responses feel connected instead of isolated

Conversational Retrieval Flow
(User query + history → query enhancement → retrieval → answer)

Conversational Retrieval Flow

2. Page-Aware Search

One thing becomes very obvious once we start testing real documents:

Not every query should be handled using semantic search.

The problem

If a user asks:

“What is written on page 5?”

A pure vector search might return:

  • Content from page 3 that looks semantically similar
  • Completely miss the actual page

This is technically “correct” from a similarity perspective, but practically wrong.

The fix: introduce a deterministic path

Instead of forcing everything through FAISS, we add a second mode.

Detecting page intent

page_match = re.search(r"pages+(d+)", query.lower())
target_page = int(page_match.group(1)) if page_match else None

Restricting search space

allowed_pages = [target_page - 1, target_page, target_page + 1]

candidates = [
    item for item in text_metadata
    if item["page"] in allowed_pages
]

Why this works well

  • removes ambiguity
  • reduce noise in retrieval
  • align results with user intent

It’s a simple idea, but it has a big impact on reliability.

Final behavior

  • Page-specific queries → deterministic filtering
  • General queries → semantic search (FAISS + rerank)

Page-aware vs Semantic Flow

Page-aware vs Semantic Flow

3. Handling Follow-Up Queries

This is where the system starts to feel more natural.

The problem

A query like:

Explain more

has no standalone meaning.

Without additional context, retrieval either fails or returns random results.

Detecting vague queries

vague_followups = re.compile(
    r"^(explain(s+w+){0,3}|elaborate|tell me more|go on|continue|...)",
    re.IGNORECASE
)

Injecting context from previous answers

last_pages = get_last_referenced_pages(st.session_state.messages)

if last_pages:
    page_inject = last_pages[len(last_pages) // 2]
    query = f"{query} page {page_inject}"

What this achieves

A vague query like:

Explain more

gets transformed into something like:

Explain more page 5

Now retrieval has something concrete to work with.

Result

  • Follow-up queries become usable
  • Conversations feel continuous
  • Retrieval remains grounded in the document

Follow-up Handling Flow

Follow-up Handling Flow

4. Debugging the RAG Pipeline

This is probably the most important upgrade in this part.

Most RAG systems fail not because they are fundamentally broken, but because we can’t see what’s happening inside them.

The usual situation

We get a wrong answer and we don’t know:

  • Was the query bad?
  • Was retrieval wrong?
  • Did reranking fail?
  • Did the model hallucinate?

Everything looks like a black box.

Adding visibility

So, we introduce a debug layer that exposes each stage.

1. Query transformation

debug_data["query"] = query
debug_data["search_query"] = search_query

This lets us compare:

  • Original query
  • Final query used for retrieval (after HyDE / modifications)

Here’s what this looks like in practice:

Query Analysis Panel

2. FAISS retrieval results

distances, indices = index.search(query_vector.reshape(1, -1), k=FAISS_SEARCH_K)

Here’s what this looks like in practice:

FAISS Results

3. Reranking results

results = ranker.rerank(RerankRequest(query=query, passages=rerank_items))

Here’s what this looks like in practice:

Re-Rank Results

4. FAISS vs rerank comparison

This is where things get interesting.

We can now see cases where:

  • FAISS ranks something high
  • Rerank pushes it down

Or vice versa.

Here’s what this looks like in practice:

FAISS vs Re-Rank Comparison

5. Score distribution

ax.plot(faiss_scores, label="FAISS")
ax.plot(rerank_scores, label="Rerank")

Here’s what this looks like in practice:

Score Distribution Graph

Why this matters

Now when something goes wrong, we can actually trace it:

  • If FAISS results are bad → embedding / chunking issue
  • If FAISS is good but rerank is bad → rerank model issue
  • If both are good → prompt or answer generation issue

This turns debugging into a structured process instead of trial and error.

Final Architecture

Final Architecture

Conclusion

At the beginning of this series, we had a simple goal: understand how RAG works by building it ourselves.

Over time, that evolved into something more practical.

We now have a system that:

  • Handles conversational queries
  • Deals with vague follow-ups
  • Respects document structure
  • Provides visibility into retrieval

More importantly, It’s no longer a black box — it’s a system you can reason about.

What changed

We moved from a basic pipeline:

Search → Answer

to something closer to:

Understand → Retrieve → Validate → Explain → Debug

Where this leaves us

This is no longer just a learning project. It’s a foundation we can build on.

What’s next

In the next series, we’ll move beyond retrieval and look at something more powerful:

  • Tool-using AI systems
  • Offline LLM capabilities
  • Building agents that can take actions

Code

Main branch:
https://github.com/SharathKurup/chatPDF

If you’ve followed along from Part 1 to here, you’ve already done the hard part — building the system from scratch and understanding how it behaves.

From here, it’s no longer about understanding RAG — it’s about building on top of it.

Taming the Spike: Predicting Glucose Peaks 30 Minutes Ahead with Transformers and TensorFlow 🩸🚀

Managing blood glucose is like trying to drive a car where the steering wheel has a 20-minute lag. For people living with Type 1 or Type 2 diabetes, Continuous Glucose Monitoring (CGM) devices like Dexcom or FreeStyle Libre provide a stream of data, but reacting to a high sugar spike after it happens is often too late.

In this tutorial, we are diving deep into Transformer-based CGM prediction and deep learning for time-series forecasting. We will leverage the Attention mechanism to model long-range dependencies in glucose data, allowing us to predict hyperglycemic events 30 minutes before they occur. By using a stack featuring TensorFlow/Keras, Pandas, and InfluxDB, we’ll move beyond simple linear regression into the world of state-of-the-art sequence modeling.

Why Transformers for Glucose Data?

Traditional models like LSTMs (Long Short-Term Memory) are great, but they process data sequentially. Glucose levels are influenced by factors with varying time horizons—a meal consumed 3 hours ago might still be impacting your levels, while a sudden burst of exercise affects you instantly.

The Transformer architecture uses self-attention to weigh the importance of different time steps simultaneously, making it exceptionally good at capturing these non-linear fluctuations.

The System Architecture

Here is how the data flows from a wearable sensor to a proactive alert:

graph TD
    A[CGM Sensor: Dexcom/Libre] -->|Raw Data| B(InfluxDB)
    B -->|Time-Series Query| C[Pandas Preprocessing]
    C -->|Feature Engineering| D[Transformer Encoder]
    D -->|Multi-Head Attention| E[Flatten/Dense Layers]
    E -->|Output| F{30-Min Prediction}
    F -->|Value > 180mg/dL| G[Hyperglycemia Alert 🚨]
    F -->|Stable| H[Normal Monitoring]

Prerequisites

Before we get our hands dirty with code, ensure you have the following installed:

  • TensorFlow 2.x
  • Pandas & NumPy
  • InfluxDB Python Client (for handling high-frequency time-series data)

Step 1: Data Ingestion from InfluxDB

Glucose data is essentially a time-series of values (usually measured every 5 minutes). InfluxDB is the gold standard for storing this kind of IoT data.

import pandas as pd
from influxdb_client import InfluxDBClient

# Connecting to our health data lake
client = InfluxDBClient(url="http://localhost:8086", token="MY_TOKEN", org="HealthLab")
query_api = client.query_api()

query = '''
from(bucket: "cgm_data")
  |> range(start: -7d)
  |> filter(fn: (r) => r["_measurement"] == "glucose")
  |> pivot(rowKey:["_time"], columnKey: ["_field"], valueColumn: "_value")
'''

df = query_api.query_data_frame(query)
# Convert time to index and resample to ensure 5-minute intervals
df['_time'] = pd.to_datetime(df['_time'])
df = df.set_index('_time').resample('5T').mean().interpolate()

Step 2: Building the Transformer Block

The heart of our model is the Multi-Head Attention layer. This allows the model to “attend” to specific past events (like a high-carb lunch) when predicting the future.

import tensorflow as tf
from tensorflow.keras import layers

def transformer_encoder(inputs, head_size, num_heads, ff_dim, dropout=0):
    # Normalization and Attention
    x = layers.LayerNormalization(epsilon=1e-6)(inputs)
    x = layers.MultiHeadAttention(
        key_dim=head_size, num_heads=num_heads, dropout=dropout
    )(x, x)
    x = layers.Dropout(dropout)(x)
    res = x + inputs

    # Feed Forward Part
    x = layers.LayerNormalization(epsilon=1e-6)(res)
    x = layers.Conv1D(filters=ff_dim, kernel_size=1, activation="relu")(x)
    x = layers.Dropout(dropout)(x)
    x = layers.Conv1D(filters=inputs.shape[-1], kernel_size=1)(x)
    return x + res

Step 3: Assembling the Prediction Model

We will feed the last 12 readings (1 hour of data) to predict the glucose level 30 minutes (6 steps) into the future.

def build_model(input_shape, head_size, num_heads, ff_dim, num_transformer_blocks, mlp_units, dropout=0, mlp_dropout=0):
    inputs = tf.keras.Input(shape=input_shape)
    x = inputs

    for _ in range(num_transformer_blocks):
        x = transformer_encoder(x, head_size, num_heads, ff_dim, dropout)

    x = layers.GlobalAveragePooling1D(data_format="channels_last")(x)
    for dim in mlp_units:
        x = layers.Dense(dim, activation="relu")(x)
        x = layers.Dropout(mlp_dropout)(x)

    outputs = layers.Dense(1)(x) # Predicting the single scalar value
    return tf.keras.Model(inputs, outputs)

# Hyperparameters
input_shape = (12, 1) # 12 time steps, 1 feature (glucose)
model = build_model(input_shape, head_size=256, num_heads=4, ff_dim=4, num_transformer_blocks=4, mlp_units=[128], dropout=0.1)

model.compile(optimizer="adam", loss="mse", metrics=["mae"])
model.summary()

The “Official” Way: Production Patterns

While this model is a great start, productionizing health-tech AI requires rigorous validation, Kalman filters for noise reduction, and edge deployment strategies.

For advanced architectural patterns on medical time-series and production-ready deep learning pipelines, I highly recommend checking out the deep-dives at WellAlly Blog. They cover everything from HIPAA-compliant data ingestion to real-time inference optimization for wearables. 🥑

Step 4: Training & Results

When training, it’s vital to use a sliding window approach. We don’t just want to predict the next value; we want to predict the value $t+6$.

# Quick snippet for windowing
def create_windows(data, window_size, horizon):
    X, y = [], []
    for i in range(len(data) - window_size - horizon):
        X.append(data[i:i+window_size])
        y.append(data[i+window_size+horizon])
    return np.array(X), np.array(y)

# Assuming 'values' is our normalized glucose array
X_train, y_train = create_windows(normalized_values, 12, 6)

history = model.fit(X_train, y_train, epochs=50, batch_size=32, validation_split=0.2)

Evaluation

In testing, this Transformer model typically achieves a Mean Absolute Relative Difference (MARD) significantly lower than traditional ARIMA models, especially during the “post-prandial” (after meal) phase where glucose volatility is at its peak.

Conclusion

By using Transformers, we shift from “What is my sugar now?” to “Where will my sugar be in 30 minutes?”. This proactive window gives users enough time to take a corrective dose of insulin or go for a quick walk, effectively flattening the glucose curve.

What’s next?

  1. Feature Augmentation: Add insulin-on-board (IOB) and carb-on-board (COB) as additional input features.
  2. Uncertainty Estimation: Use Monte Carlo Dropout to provide a confidence interval with the prediction.

Are you working on health-tech or time-series AI? Drop a comment below or share your thoughts on the latest CGM trends! 🚀💻

For more technical insights and advanced health-tech tutorials, visit wellally.tech/blog.

Local AI on the move

This is a submission for the Gemma 4 Challenge: Write About Gemma 4

Of late, Google has released intelligent open AI models-Gemma 4.
For the first time AI behind cloud infrastructure is supposably being accessible on the edge realistically. While exploring browser privacy concepts in my recent project, I understood the importance of AI running directly on the devices however since the advent of AI, the powerful open models felt distant to be used locally. I used media pipe for the local privacy shield but there were too many restrictions which I was unable to tackle and as an AI practitioner and dealing with implementation of ML pipelines often I am not someone who has expertise in security and if billions of parameters during inference preserved on the hardware can work effectively then there is possibility of acceleration of rise in Personal AI.
I know many of my colleagues will argue with me that Am I strange to capabilities of Cloud? No!
Since we know edge computing reduces latency in enabling important communication such as in relation to defense and medicine, i should say we should rely a bit less on Cloud infrastructure and make our edge computing paradigm stronger.

Personal AI can be thought as analogous to Personalised Medicine. In traditional medicine where each person has different response to medications people need medicine and healthcare exclusive and individualistic. Scientists, Researchers, hospitals and industries all of them are working on Personalised medicine similarly Personalised AI will enhance the human creativity manifold which will not only train on the users’ context but will remain capable of fetching world’s information relevant, useful and novel. From security to educating on the ground level AI enabled IOT using open models like Gemma 4 will reach the remote and rural areas. The invention of AI technology has itself increased the educated masses informed, creative and enthusiastic to new things. When knowledge was far fetched concept for people who were not belonging to the premium locations in the country/countries we found online content spreading like lightening speed a few years back but AI and cloud has done wonders to the human productivity. AI can help you with anything no matter which field you are in!

What about Gemma 4 and what it can do in the upcoming times

Gemma 4 is trained on billions of parameters having longer context and superb mathematical capabilities
26B and 31B models for your personal computers
26B is great for lightweight multimodal experiments, local assistants, summarization and RAG systems effectively
Developers can choose their models according to their use case and get most of it.

Let’s come to 31B which is having better reasoning than it’s previous counterpart can be used for complex coding, advanced reasoning which we need [(sarcastic): do not trade off your reasoning for real.
both on 80GB NVIDIA H100 GPU

E2B and E4B models: The concept of AI everywhere
The peculiarity is that they do not waste battery life because of their lightweight nature and I found it interesting to bypass sensitive cloud processing, good use case is speech recognition and understanding OCR because of best native audio and video processing.

These models are optimized by the technique of quantization which reduces the memory and computational requirements of large models capable of running on the consumer hardware…ok now I can get the inferences locally wonderful!

Future scope

  • low resource environments will get benefitted
  • security shall be redefined
  • local healthcare assistance

Challenges

  • Deployment complexity of lightweight open models still persist but you can refer Google Keyword for the new releases for the sake of simplicity.
  • Energy usage is real as well as hardware cost will be high in initial years

It is a good news for researchers you do not need to rely on API, research labs and gives you more capabilities to build prototype and study model behaviour. Infrastructure dependency is getting minimal here.

Bizbox Build Log: May 11–15, 2026

Week of 2026-05-11 · Releases v0.0.13 → v0.0.20 · 15 merged PRs · 8 releases

Shipped this week

Human-in-the-loop handoff, end to end

This week’s headline: the full agent → human → agent cycle is now wired. Three PRs closed the loop together.

#38 — Human handoff logging and notification (v0.0.13, @adPalafox)
Bizbox now emits a dedicated event when an issue parks waiting for a human (confirmation request, question, or human-owned blocker). Events deduplicate across runs to avoid notification spam and feed the inbox badge count. Everything else this week builds on this foundation.

#42 — ClickUp awaiting-human approval polling (v0.0.16, @adPalafox)
Once an issue is parked, Bizbox polls the ClickUp chat message posted for that handoff. A direct reply or positive reaction is detected and bridged back as an approval signal. Configurable reaction set, deduplication, and test coverage included.

#51 — Confirmation notifications in the inbox (v0.0.20, @angelofallars)
“Confirmation requested” and “Questions requested” items now appear in the board inbox, and the sidebar badge counts them. Operators no longer need to hunt for parked issues; they show up alongside other actionable work.

The result: agent parks → ClickUp message sent → human replies → Bizbox detects it → agent resumes.

ClickUp super agents

#36 — ClickUp super agents (v0.0.20, @ralphbibera)
The clickup_agent_ref adapter wires Bizbox to ClickUp-native automations as a first-class agent surface. It runs as an API-first bridge (not a local process executor), shapes ClickUp task payloads with full issue context, and supports an automation_trigger mode so ClickUp Automations can hand off to the ClickUp AI agent without browser automation.

Audience control for deliverables and documents

#50 — Audience support for deliverables and issue documents (v0.0.19, @adPalafox)
Deliverables and issue documents now carry an explicit audience field: human (public-facing) or internal (team-only). Schema, types, API validation, and board UI all updated. Agents can now produce internal work products (triage queues, dry-run previews) alongside public drafts without mixing them on the same surface.

Deliverables from heartbeat runs

#49 — Deliverables created on heartbeat (v0.0.18, @DennisDenuto)
Heartbeat run summaries can now promote durable text sections into issue documents automatically. Both explicitly tagged blocks and legacy deliverable sections work. Agents no longer need a separate write step to surface structured work products.

Timeout configuration for the OpenClaw adapter

#54 — Timeout configurations and delayed responses (v0.0.20, @adPalafox)
The OpenClaw Gateway adapter gained agentAcceptTimeoutMs, separating agent-acceptance timing from connection-level timeouts. Default behaviors were clarified and edge-case test coverage added. Operators running long-running agent tasks now have finer control over when Bizbox considers a connection stalled.

Citro brand refresh

#35 — Citro branding (v0.0.14, @ralphbibera)
The board UI got a new coat of paint: warmer dark palette, metallic orange accents, rounder surfaces. A new TopNavItem component handles the top bar, and a brand-shell CSS class anchors the palette across Layout, Sidebar, and BreadcrumbBar. The breadcrumb and top-nav components were refactored as part of the same pass.

Fixes and polish

Decisions

awaiting_human is not blocked. The team split these into distinct states. Dependency blockers can resolve without human input; human-decision blockers require an explicit handoff and a clear ask. Conflating them made notification routing impossible and obscured how long humans were actually in the critical path. awaiting_human is now a protected control-plane pause. (The full architectural analysis is in the May Deep Dive draft; post coming next week.)

ClickUp is a signal surface, not a source of truth. The polling bridge (#42) was designed with a deliberate constraint: a ClickUp reply or reaction is only a signal until Bizbox accepts the matching request_confirmation interaction. The Bizbox issue graph stays authoritative, preventing race conditions where a ClickUp reaction fires before the interaction is registered.

audience is explicit, not inferred. Rather than deriving visibility from document type or location, the team added a first-class audience field. Public drafts default to human; agents producing internal work products must explicitly set internal. Leakage becomes harder to do accidentally.

Trade-offs

Polling instead of webhooks for ClickUp approval. The bridge polls for replies and reactions rather than receiving webhooks. This adds latency bounded by the poll interval and burns API quota. The trade-off was deliberate: ClickUp’s webhook surface for chat reactions is less reliable than its REST API, and a working bridge now beats a fragile one later. A webhook upgrade is the natural next step once polling is proven in production.

Heartbeat-promoted deliverables are best-effort. The extraction in #49 uses pattern matching on run output. Agents that don’t follow the tagging convention will have deliverables silently skipped rather than errored. That was a deliberate choice to avoid breaking existing heartbeat runs. The feature’s value depends on consistent tagging adoption.

Open challenges

ClickUp approval latency in production. The polling bridge is new and untested at scale. Safe poll intervals and false-positive rates for the “positive reaction” heuristic are unknown. Monitoring the first week of production use is the immediate next step.

Deliverable tagging adoption. There’s no enforcement yet. An agent producing a deliverable in a non-standard format will silently miss promotion. A linting pass or schema validation on run output would close this gap.

Builder API route migration. Moving the builder under company routes (#47) is the right long-term shape, but clients that hardcoded the old instance-root path will break silently. Known consumers should be audited before the next release.

Just Before Snowflake Summit 26: From an AI Perspective – The Current State of “Snowflake – The AI Data Cloud”

Note:
This article represents my personal views and not those of Snowflake.

Information regarding Snowflake Summit 26

Snowflake Summit 26 will be held in San Francisco from June 1 to June 4, 2026. Various updates are expected to be announced, so please stay tuned.


Snowflake Summit 26

Explore the future of data, AI, and applications at Snowflake Summit 26. Join experts, attend workshops, and get SnowPro certified while learning new data trends.

favicon
snowflake.com

I am planning to attend in person, so I look forward to meeting anyone who will be there!

Introduction

As mentioned at the beginning, Snowflake Summit 26 is finally approaching next month. In this article, I would like to provide an overview of the current standing of Snowflake – The AI Data Cloud from an AI perspective and broadly organize the situation as of May 17, 2026. In my professional role, I have had many opportunities to discuss these topics recently, so I decided to verbalize them in an article. Please note that this article is intended to summarize the overall picture and may not cover every single detail. Let us dive in!

There is No AI Strategy Without a Data Strategy

“There is no AI strategy without a data strategy” – Interestingly, the reason I chose to join Snowflake about a year ago was very close to this. Even then, there were many requests to utilize AI in the enterprise, but I felt that a well-organized and easy-to-use data foundation was necessary for that. Recently, keywords like ChatGPT and Claude have become common, but these services—and the models behind them—do not inherently possess the “context of the company trying to use them” in their raw state. They become more useful within a company by combining them with internal data. However, to do so, it is necessary to prepare the data foundation and utilize it as appropriate context.

Given this situation, I believe “There is no AI strategy without a data strategy” is a keyword that truly captures the essential point.

Two Pillars of AI Utilization in Snowflake

Snowflake overview

Regarding how AI can be utilized in Snowflake under these circumstances, I believe there are two main pillars. These are “Making data AI-Ready/analyzable” and “Using AI-Ready data.”
In the diagram above, these correspond to the left and right sides of “AI Ready GOLD.” Let me organize these two pillars below.

AI Utilization for Making Data AI-Ready/Analyzable

Snowflake is expanding its features to enable the use of AI in various ways to make data AI-Ready or analyzable.

Data Engineering Perspective

It is said that 80% of the world’s data is unstructured data, such as images, videos, and PDFs. Snowflake is also expanding various functions to handle this unstructured data. By using features like AI Functions and the Document Processing Playground, it is possible to convert unstructured data into analyzable data.

AI Functions include the following types of functions:
Cortex AI Functions

By using these, for example, it is possible to perform the following processing based on audio recording data:
Extract from audio data

This allows various data points to be generated from a single recording and treated as analytical dimensions.

Handling Document Data

Furthermore, it is now possible to handle various document data, including PDFs. By using the AI_PARSE_DOCUMENT function, the following conversion process can be performed:
AI_PARSEDOCUMENT
AI_PARSE_DOCUMENT supports various file formats such as PDF, PPTX, DOCX, JPEG, JPG, PNG, TIFF, TIF, HTML, and TXT.

An update on May 4, 2026, enhanced the OCR mode of AI_PARSE_DOCUMENT, improving the accuracy of OCR mode and multilingual support. Please give it a try.

May 04, 2026: AI_PARSE_DOCUMENT OCR quality improvements

Additionally, the Document Processing Playground feature has been released. This feature helps you by suggesting what SQL or Python code to write when uploading document data to extract necessary information.

Updates for these functions handling document data are frequent, and features such as figure/table extraction have recently been released. These functions are also introduced in the following blog posts (Note: Links are to Japanese articles).

By vectorizing the data extracted using these functions, semantic search based on meaning becomes possible. This can be used with the Cortex Search feature, which will be described later.

Handling PII (Personally Identifiable Information)

The AI_REDACT AI Function for processing personal information has also been released.
This function identifies and masks PII contained within text. The image below illustrates the concept:
AI_REDACT

Handling Video and Audio Data

Additionally, as of May 6, 2026, although in Public Preview (PuPr) status, it has become possible to directly handle video and audio data using specific models in the AI_COMPLETE function. While there are limitations on models and file sizes, the patterns for approaching unstructured data have increased further.

May 04, 2026: Multimodal video and audio analysis for marketing and brand insights (Public Preview)

A detailed analysis of the results can be found in the blog post “Beyond Transcription – Multimodal Video and Audio Analysis with Snowflake AI_COMPLETE” so please take a look.

Regarding audio data, it was already possible to convert it to text using the AI_TRANSCRIBE function, but the variations have now expanded.

A great advantage of these AI Functions is that they can be executed as part of SQL close to the data, allowing for efficient processing of large volumes of data.
In this way, Snowflake provides various services for handling unstructured data, enabling conversion into AI-Ready and other easily analyzable formats. I believe this reflects a design philosophy of “AI utilization close to the data.”

AI Utilization for People and Systems to Use AI-Ready Data

For data organized in the manner described above, Snowflake provides various ways to utilize that data. While traditional data handling using SQL and BI tools remains possible, AI has come to play a significant role in the data utilization field. Snowflake provides the following major services as related functions:

  • Services for searching data: Cortex Search, Cortex Analyst
  • Services for developing arbitrary AI Agents to search data or gain insights: Cortex Agents
  • Applications for working with data: Snowflake Intelligence, Cortex Code in Snowsight / CLI
  • Integration with other AI tools: Snowflake-managed MCP Server

Services for Searching Data

Cortex Search

Cortex Search is a hybrid search service supporting both keyword and vector search. Cortex Search is receiving useful updates, such as Cortex Search Multi-index and Index-specific Boosts to enhance search flexibility and accuracy, as well as Cortex Search Batch, which covers use cases for processing large volumes of queries in batches, such as entity resolution, catalog mapping, and deduplication.

Cortex Analyst

Cortex Analyst is a service for achieving Text-to-SQL (converting natural language into SQL). It utilizes defined Semantic Views and leverages AI to perform searches against table data.
In analytical tasks and AI-Ready data utilization, the Semantic Layer is a crucial element. In Snowflake, this feature is named “Semantic View,” allowing for the organization of metadata such as logical tables, analytical dimensions, and items to be aggregated. Additionally, Snowflake has a feature called Semantic View Autopilot that automatically generates these “Semantic Views.” Currently, generation is in English, so care is needed, but it is a feature that assists in the often labor-intensive task of preparing Semantic Views.

A part of the Semantic View Autopilot feature includes automatically generating Semantic Views by importing definition information from other tools. For example, it can read a Tableau Workbook to automatically generate a Semantic View.

Furthermore, Snowflake is advancing an initiative called the Open Semantic Interchange (OSI) Initiative, working with various partners to standardize the Semantic Layer. The repository for this activity is below:

open-semantic-interchange/OSI

Services for Developing Arbitrary AI Agents to Search Data or Gain Insights

Cortex Agents

Cortex Agents

Cortex Agents is a service for building AI Agents on Snowflake. It functions as an AI Agent that operates by linking data search services like Cortex Search and Cortex Analyst with custom tools such as stored procedures. In a recent update, Cortex Agents added support for Agent skills, improving execution efficiency for repetitive tasks, and support for MCP Connectors, allowing integration with external tools and services.

Cortex Agents can be used not only within Snowflake Intelligence but also via REST API or through a Snowflake-managed MCP Server, allowing calls from any application or AI Agent.
Examples of integration include:

Recently, on April 13, 2026, an update was made allowing Cortex Agents to directly reference Semantic Views and generate SQL without going through Cortex Analyst. This update is expected to improve the accuracy of analytical queries and reduce latency.

Apr 13, 2026: Improved SQL generation in Cortex Agents

Applications for Working with Data

Snowflake Intelligence

Snowflake Intelligence

Snowflake Intelligence is a service that allows users to perform deep dives into data by querying the organized data foundation on Snowflake using natural language. Cortex Agents operate behind this application. With the support for Agent Skills and MCP Connectors mentioned above, these can also be utilized within Snowflake Intelligence. Furthermore, as mentioned in recent press releases, there are many feature updates for business use, such as the DeepResearch feature for in-depth investigations (scheduled for PuPr soon) and the Artifact feature for managing and sharing generated charts and tables (scheduled for GA soon).

Snowflake Intelligence is also used internally at Snowflake, with over 6,000 members across various roles using the tool. A behind-the-scenes look at this build has been published on Medium as “From Data Maze to Intelligence Layer: GTM AI Assistant with Semantic Views on Snowflake Intelligence“.

Cortex Code in Snowsight / CLI

Cortex Code in Snowsight / CLI is an AI Agent tool that supports various development tasks on Snowflake. In addition to such tasks, it can be used for data discovery via Horizon Catalog (Snowflake’s native catalog feature), allowing for data exploration using Cortex Code against the data organized on Snowflake.

Similar to Snowflake Intelligence, Cortex Code is utilized by internal members at Snowflake. The appearance of these AI tools seems to have increased the utilization of the internal data foundation. In fact, I have personally started using Cortex Code frequently to utilize internal data.

Recent updates for Cortex Code include:

  • Support for more external data systems like AWS Glue, Databricks, and Postgres
  • Support for MCP and Agent Communication Protocol (ACP)
  • New VS Code extension (in Private Preview) and Claude Code plugin
  • New Agent Software Development Kit (SDK) supporting Python and TypeScript, allowing Cortex Code features to be integrated directly into your own apps or workflows
  • Updates to Cortex Code on Snowsight:
    • Cloud Agents (in Private Preview) allow users to execute code and run workflows directly in the browser
    • New Plan Mode allows for previewing and approving workflows before execution
    • Snap & Ask feature allows direct interaction with data artifacts like charts and tables

For Claude Code users, please try the snowflake-cortex-code plugin mentioned above.

Snowflake Cortex Code – Claude Marketplace

Integration with Other AI Tools

Snowflake allows several functions to be published as a Managed MCP Server on Snowflake.
Snowflake Managed MCP Server

This MCP Server can be used as a remote MCP Server. It can be utilized from AI Agent tools acting as MCP Clients, including ChatGPT, Claude Desktop, and Claude Code.

Security and Governance Supporting AI Utilization

The above summary focused primarily on AI for data utilization on Snowflake. Snowflake also covers security and governance elements in this AI utilization. As the use of AI advances further, these elements will become extremely important.
governance

I personally consider Snowflake RBAC (Role-Based Access Control) to be very powerful. As shown in the diagram above, when using various services and features related to AI, the same RBAC managing the data is applied, and access control is performed based on the roles linked to the user. Since all answers reflect only the data the user has permission to view, it is possible to utilize AI and data under appropriate governance.

Furthermore, Snowflake has observability features centered on AI Observability. For example, various logs related to Cortex Agents are managed here. Additionally, a quality evaluation feature called Cortex Agents Evaluation has been released, allowing for the quality assessment of AI Agents using the GPA framework. The GPA framework evaluates AI Agent quality based on Goal (is the user’s objective eventually achieved?), Plan (do planning and re-planning provide effective high-level instructions?), and Act (do the agent’s actions follow the plan, call tools appropriately, and progress toward the goal?).

From a budget management perspective, budget management features for Cortex Agents / Snowflake Intelligence have been released (GA on April 10, 2026). This allows for:

  • Flexible tag-based scope settings – management by department or project
  • Multi-stage threshold settings – defense-in-depth combining ACTUAL and PROJECTED
  • Automated access control – automatic response when thresholds are reached
  • Cycle-based management – automatic reset/recovery at the start of the month

Other features like row-level policies also serve as a foundation, with various AI-related elements being built upon them.

Updated on May 17, 2026

On May 14, 2026, Cortex AI Guardrails expanded its support beyond Cortex Code to include Snowflake Intelligence and Cortex Agents. Cortex AI Guardrails is part of the Snowflake Horizon Catalog and is designed to use context-based reasoning to detect and neutralize threats such as indirect prompt injections embedded in tool calls. Although the configuration is applied at the account level, it can be easily enabled by changing the AI_SETTINGS parameter.

May 14, 2026: Cortex AI Guardrails support for Snowflake Intelligence and Cortex Agents (General availability)

This enhancement enables you to use these capabilities even more securely, so we encourage you to consider adopting it as well.

Conclusion

Recently, the paper that marked the beginning of Snowflake, “The Snowflake Elastic Data Warehouse,” received the SIGMOD Test-of-Time Award.

I personally feel that the evolution of Snowflake as a service over the years is proving its worth in the current era of AI.
In transforming enterprise operations, data and AI are inseparable. Snowflake provides Cortex AI based on the concepts of being easy, efficient, and trusted. I hope you will fully utilize Snowflake’s capabilities as a platform where you can easily and efficiently leverage AI while maintaining governance and security close to your data.
Snowflake has many feature updates, and it is difficult to cover them all, but I hope this article helps you grasp the overall current state of AI utilization in Snowflake.

And as mentioned at the beginning, Snowflake Summit 26 will finally be held from June 1 to June 4, 2026. I am very much looking forward to what will be announced!

Appendix

Snowflake server release notes and feature updates

Recent feature releases are summarized on this page. Please take a look.

Snowflake What’s New Distribution (by tsubasa-san)

tsubasa-san distributes update information for Snowflake’s “What’s New” on X. Please follow to catch up on the latest information.

Japanese Version

Snowflake What’s New Bot (Japanese)

English Version

Snowflake What’s New Bot (English)

Japanese version

Revision History

May 17, 2026: Initial post

Knock a new alternative to Insomnia, postman and more…

Workspace manager for your requests

I am a bit tired of skip the license process on all tools, when I want to use some tools I need to use my TC or use the app in a poorly experience, that is the reason I created “knock”, I’ll be honest, the tool is for me, but I hope maybe could be useful for you, some screenshots are bellow

Workspace manager for your requests

Tools

JWT validator

Tools available close to you, JWT validator

Base64

base 64

Typical requests view

Project view

Version your workspace and share

Use git to manage your projects

manage projects

k8s

Some extra tools for k8s, like Kubeconfig manifest encripted, and allow you to organize that chaos. Load a shell with your cluster and the shell allows mouse-based cursor positioning.

k8s manifests manager

Shell included

If you read at this point, please give me a ⭐️ in the repository, you have not idea how important is this for all opensource contributors 🤗

Install

Desktop app — Quick install (Linux / macOS)

One-liner. Resolves latest release, downloads the right asset for your OS/arch, installs it, and (after confirming) strips macOS Gatekeeper quarantine.

curl -fsSL https://raw.githubusercontent.com/jairoFernandez/knock/main/scripts/install-app.sh | bash

Pin a version:

curl -fsSL https://raw.githubusercontent.com/jairoFernandez/knock/main/scripts/install-app.sh | bash -s -- --version v0.1.0

Linux: defaults to .AppImage. Switch to .deb or .rpm (require sudo):

curl -fsSL https://raw.githubusercontent.com/jairoFernandez/knock/main/scripts/install-app.sh | KNOCK_APP_FORMAT=deb bash

Desktop app — Quick install (Windows)

PowerShell. Downloads .msi and runs it.

iwr https://raw.githubusercontent.com/jairoFernandez/knock/main/scripts/install-app.ps1 | iex

Silent install:

$env:KNOCK_SILENT = "1"
iwr https://raw.githubusercontent.com/jairoFernandez/knock/main/scripts/install-app.ps1 | iex

Knock

Buy Me A Coffee
GitHub Sponsors

HTTP client + workspace toolkit. Ships as a CLI (knock) and a Tauri desktop app (Knock).

Workspace layout:

apps/knock-app    Tauri 2 desktop app (React + Vite frontend)
crates/knock-cli  knock CLI binary
crates/knock-core Shared core library

Install

Quick install (Linux / macOS — CLI)

One-liner. Downloads the latest release for your OS/arch, places knock in ~/.local/bin, and (after confirming) strips the macOS Gatekeeper quarantine attribute so the unsigned binary can run.

curl -fsSL https://raw.githubusercontent.com/jairoFernandez/knock/main/scripts/install.sh | bash

Pin a version:

curl -fsSL https://raw.githubusercontent.com/jairoFernandez/knock/main/scripts/install.sh | bash -s -- --version v0.1.0

Custom prefix:

curl -fsSL https://raw.githubusercontent.com/jairoFernandez/knock/main/scripts/install.sh | KNOCK_PREFIX=/usr/local/bin bash

If ~/.local/bin is not in your PATH, add it:

export PATH="$HOME/.local/bin:$PATH"

Quick install (Windows — CLI)

PowerShell. Installs to %LOCALAPPDATA%Knockbin and adds it to user PATH.

iwr https://raw.githubusercontent.com/jairoFernandez/knock/main/scripts/install.ps1 | iex

Pin…

When the Canary Sings: CISA Flags Cisco SD-WAN CVE-2026-20182 — Here’s What Your SOC Needs to Do Before Monday

TL;DR

  • CVE-2026-20182 just landed on CISA’s Known Exploited Vulnerabilities (KEV) catalog — meaning attackers are actively exploiting admin-access flaws in Cisco SD-WAN appliances right now, and the binding operational directive clock is ticking for federal agencies with a hard patch deadline.
  • KEV listing is the only prioritization signal that matters — a CVSS 9.8 with no exploitation evidence is theoretical risk; a CVSS 7.5 on KEV is an incident-in-progress. If your vulnerability management program still sorts by score instead of KEV status, this is your wake-up call.
  • SD-WAN devices are the worst-case target — internet-facing by architectural necessity, sitting at the network edge bridging branch offices to corporate WAN, and often managed through interfaces that were never designed to face the public internet unshielded.
  • Patching is necessary but insufficient — assume compromise on any internet-exposed SD-WAN appliance, hunt for indicators of post-exploitation activity, and treat this as a compromise assessment, not a patch cycle.

The KEV Catalog Is Not a Watchlist — It’s a Crime Scene Report

When CISA adds a vulnerability to the Known Exploited Vulnerabilities catalog, it is not issuing a gentle advisory. It is publishing an intelligence finding: we have confirmed evidence that threat actors are using this flaw to compromise real systems. For enterprise security architects, this distinction reshapes the entire response calculus.

KEV, established under Binding Operational Directive 22-01, was designed to solve a crisis that has plagued security operations for over a decade: the industry has been trapped in a CVSS-driven hamster wheel — tens of thousands of CVEs, a fat tail of critical-severity findings, and scanners that scream about everything and prioritize nothing. CISA’s intervention was blunt: stop guessing what attackers might use, and start responding to what they are using.

CVE-2026-20182 joins a catalog of vulnerabilities with confirmed exploitation. For federal agencies, this triggers a mandatory remediation deadline — typically two to three weeks. But KEV’s influence extends far beyond .gov. Private-sector security leaders treat it as the authoritative prioritization signal because it eliminates the ambiguity CVSS scores alone cannot resolve. A vulnerability on KEV is not a theoretical risk; it is an active attack vector with real victims.

Security architects should internalize this: if your vulnerability management SLAs are defined by CVSS severity bands, you are optimizing for the wrong variable. A CVSS 9.1 without exploitation belongs in the standard patch cycle. A CVSS 6.8 on KEV belongs in the incident response queue.

Why SD-WAN Appliances Are the Perfect Target

Cisco SD-WAN appliances occupy a uniquely dangerous position in enterprise architecture. Unlike internal servers that benefit from layers of segmentation and monitoring, SD-WAN edge devices sit at the perimeter — often directly internet-facing, terminating VPN tunnels from branch offices and remote sites. They are reachable from the outside by design.

This creates a nightmare scenario when admin-access vulnerabilities are weaponized. Administrative interfaces on network infrastructure grant the highest level of control: modify routing tables, intercept traffic, disable logging, and pivot laterally into protected networks. An attacker who achieves admin access on an SD-WAN concentrator holds the keys to every branch office connected through it.

The attack surface is broader than many organizations realize. Cisco SD-WAN — formerly Viptela, acquired in 2017 — is deeply embedded in enterprise campuses, government agencies, healthcare, and critical infrastructure. Many deployments predate zero-trust architectures, meaning administrative interfaces may have been configured under older, more permissive security models.

This follows a pattern that has defined the 2025–2026 threat landscape. Edge device exploitation has been the dominant attack vector: Ivanti Connect Secure vulnerabilities, Palo Alto PAN-OS zero-days, Fortinet SSL-VPN flaws, and now Cisco SD-WAN. Attackers have learned that perimeter devices are the highest-leverage targets — simultaneously exposed, under-monitored relative to their criticality, and often running complex software stacks with attack surfaces that outpace patching cadences.

Engineering Response: What “Prioritize” Actually Means

When a security architect tells their team to “prioritize” a KEV-listed vulnerability, that instruction must translate into concrete operational actions. For CVE-2026-20182, the response breaks down into three parallel phases.

Phase one: emergency patching. SD-WAN patching is operationally complex — these are production devices carrying live traffic, so maintenance windows are non-negotiable. But the standard change-management cycle is incompatible with a KEV-triggered threat. Security leadership must invoke emergency change procedures, and network engineering must begin staging firmware updates immediately. Organizations with redundant SD-WAN fabrics can shift traffic to alternate paths while upgrading edge devices one at a time.

Phase two: compromise assessment. The KEV listing confirms active exploitation, so patching alone is not an acceptable end state. Assume any internet-exposed SD-WAN appliance may already be compromised. Examine administrative access logs for anomalous sessions, verify no new local accounts were created, check configuration integrity against known-good baselines, and hunt for lateral movement originating from SD-WAN device IPs. If logging coverage is sparse — and for many organizations, it is — acknowledge that gap and begin closing it.

Phase three: architectural hardening. The root problem remains: admin interfaces on internet-facing network devices create unacceptable risk. Enforce MFA on all administrative access, implement IP allowlisting so management interfaces are reachable only from designated jump hosts, and move administrative interfaces out of the public routing domain via out-of-band management networks where feasible. These are zero-trust principles that should have been applied from day one — CVE-2026-20182 is the forcing function that justifies the investment.

The Broader Signal: KEV Additions Are Accelerating

For security architects tracking the macro landscape, the pace of KEV additions through 2025–2026 tells its own story. Edge devices, VPN concentrators, and network infrastructure dominate the recent additions — a clear signal that attackers have optimized their targeting around devices that are hardest to patch, easiest to reach, and most valuable to compromise.

This has implications for procurement beyond any single CVE. Organizations evaluating SD-WAN, SASE platforms, or any perimeter appliance should ask vendors hard questions: what is your mean time to patch for critical vulnerabilities? Do you provide verified indicators of compromise? Can your management plane be isolated from the data plane? Unsatisfying answers are advance warning of where the next incident will originate.

The CISO’s dilemma is well understood: patching production network infrastructure is disruptive. But the calculus has shifted. The risk of not patching a KEV-listed vulnerability on an internet-facing device is no longer probabilistic — it is confirmed, active, and measurable in incidents that have already occurred at peer organizations.

Engineering Takeaways

The addition of CVE-2026-20182 to the KEV catalog is not a routine advisory. It is a confirmed-incident notification for a vulnerability class — admin access on internet-facing SD-WAN appliances — that represents one of the highest-leverage attack paths available today. Security architects should treat this as a forcing function for three immediate actions: patch with emergency prioritization, hunt for evidence of compromise, and harden management-plane access controls as a permanent architectural fix. The KEV catalog is the canary, and it is singing. Teams that still treat vulnerability management as a CVSS-sorted backlog exercise will learn this lesson the hard way. Those that align their response tempo to KEV signals will contain the damage before it spreads.

For the complete deep-dive with implementation specifics, read the full analysis:

🔗 When the Canary Sings: CISA Flags Cisco SD-WAN CVE-2026-20182 — Here’s What Your SOC Needs to Do Before Monday

Related on Susiloharjo:

Originally published at susiloharjo.web.id. Follow for more IoT, AI, and cybersecurity architecture deep-dives.