<?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: Shailesh Vats</title>
    <description>The latest articles on DEV Community by Shailesh Vats (@shaileshvats2004).</description>
    <link>https://dev.to/shaileshvats2004</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fthepracticaldev.s3.amazonaws.com%2Fi%2F99mvlsfu5tfj9m7ku25d.png</url>
      <title>DEV Community: Shailesh Vats</title>
      <link>https://dev.to/shaileshvats2004</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/shaileshvats2004"/>
    <language>en</language>
    <item>
      <title>Vendorwake: the upstream changed, Gemma caught it, and a test proved it</title>
      <dc:creator>Shailesh Vats</dc:creator>
      <pubDate>Sun, 25 Oct 2026 12:03:30 +0000</pubDate>
      <link>https://dev.to/shaileshvats2004/vendorwake-the-upstream-changed-gemma-caught-it-and-a-test-proved-it-3o3f</link>
      <guid>https://dev.to/shaileshvats2004/vendorwake-the-upstream-changed-gemma-caught-it-and-a-test-proved-it-3o3f</guid>
      <description>&lt;p&gt;&lt;em&gt;This is a submission for the &lt;a href="https://dev.to/challenges/hacktoberfest-week3-2026-10-19"&gt;DEV Hacktoberfest 2026 Week 3 Challenge: Slow and Steady&lt;/a&gt;.&lt;/em&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  What I Built
&lt;/h2&gt;

&lt;p&gt;Every app I've shipped depends on a dozen vendors I don't control. They deprecate parameters, rename&lt;br&gt;
classes and cut major versions, and I usually find out when production does.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Vendorwake&lt;/strong&gt; is the lazy fix: an open-source engineer that reads my vendors' changelogs so I don't have&lt;br&gt;
to, and only bothers me when a change actually reaches my code. It doesn't just say "Stripe shipped&lt;br&gt;
16.0.0." It says:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;code&gt;billing/invoices.py:10&lt;/code&gt; calls &lt;code&gt;invoice.request(...)&lt;/code&gt;, which 16.0.0 removed.&lt;br&gt;
&lt;strong&gt;Confirmed:&lt;/strong&gt; the fixture's tests pass on 15.6.1 and fail on 16.0.0&lt;br&gt;
(&lt;code&gt;AttributeError: request. Did you mean: '_request'?&lt;/code&gt;). Here are the proposed patches, and here is what&lt;br&gt;
happened when I ran them.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Every finding carries one of three labels, and the label means something:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Confirmed&lt;/strong&gt;: deterministic proof. An exact symbol reference in my code &lt;em&gt;and&lt;/em&gt; a removed or renamed API,
or a test that fails under the new version.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Potential&lt;/strong&gt;: a plausible connection the model found, waiting for proof.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Unaffected&lt;/strong&gt;: the vendor or symbol isn't used.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The model can explain and downgrade a finding, but &lt;strong&gt;it cannot upgrade one&lt;/strong&gt;. That rule is enforced in code,&lt;br&gt;
not in the prompt.&lt;/p&gt;
&lt;h2&gt;
  
  
  Demo
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Live app:&lt;/strong&gt; &lt;a href="https://vendorwake-web.onrender.com" rel="noopener noreferrer"&gt;https://vendorwake-web.onrender.com&lt;/a&gt; (free Render tier: the first request after a quiet
period takes about a minute while the service wakes up)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;API docs:&lt;/strong&gt; &lt;a href="https://vendorwake-api.onrender.com/api/docs" rel="noopener noreferrer"&gt;https://vendorwake-api.onrender.com/api/docs&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The demo investigation is a real upstream change: &lt;strong&gt;stripe-python 16.0.0&lt;/strong&gt; (released 2026-09-30) against a&lt;br&gt;
small billing fixture pinned to 15.6.1. All three breaking changes reproduce offline:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Changelog item&lt;/th&gt;
&lt;th&gt;15.6.1&lt;/th&gt;
&lt;th&gt;16.0.0&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;code&gt;stripe.Reversal&lt;/code&gt; → &lt;code&gt;stripe.TransferReversal&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;exists&lt;/td&gt;
&lt;td&gt;&lt;code&gt;AttributeError&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;code&gt;StripeObject.request()&lt;/code&gt; removed&lt;/td&gt;
&lt;td&gt;exists&lt;/td&gt;
&lt;td&gt;&lt;code&gt;AttributeError&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Path params positional-only&lt;/td&gt;
&lt;td&gt;keyword accepted&lt;/td&gt;
&lt;td&gt;&lt;code&gt;TypeError: ... positional-only arguments passed as keyword&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;What the hosted run actually produced&lt;/strong&gt; (one investigation, end to end, on free tiers):&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Repository analysis&lt;/strong&gt; found &lt;code&gt;stripe==15.6.1&lt;/code&gt; in &lt;code&gt;requirements.txt&lt;/code&gt; (95% detection confidence) and
every reference by file and line: &lt;code&gt;stripe.Reversal&lt;/code&gt; in &lt;code&gt;payouts.py&lt;/code&gt;, &lt;code&gt;invoice.request(...)&lt;/code&gt; in
&lt;code&gt;invoices.py&lt;/code&gt;, &lt;code&gt;customers.retrieve(customer=...)&lt;/code&gt; in &lt;code&gt;customers.py&lt;/code&gt;, plus &lt;code&gt;catalog.py&lt;/code&gt;, which uses
Stripe but none of the affected APIs.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Discovery&lt;/strong&gt; ran two SerpApi searches, fetched the official changelog, hashed it into a TimescaleDB
snapshot, and had Gemma 4 extract &lt;strong&gt;41 changes&lt;/strong&gt; from the 16.0.0 release. The grounding check accepted
the important ones with verbatim quotes, and flagged &lt;strong&gt;4 quotes and 10 symbols&lt;/strong&gt; that Gemma had reworded
(for example, it glued a class path onto a field name). So the change is marked &lt;em&gt;needs human review&lt;/em&gt;
instead of pretending to be clean.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Version comparison:&lt;/strong&gt; in a fresh virtualenv, the fixture's tests &lt;strong&gt;passed on 15.6.1 and failed on
16.0.0&lt;/strong&gt;. That failing test is the deterministic evidence behind &lt;strong&gt;Confirmed&lt;/strong&gt; (5 deterministic
evidence items and 1 model inference on the &lt;code&gt;invoices.py&lt;/code&gt; finding).&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Patches:&lt;/strong&gt; Gemma proposed one diff per affected file. The &lt;code&gt;stripe.Reversal&lt;/code&gt; →
&lt;code&gt;stripe.TransferReversal&lt;/code&gt; diff is exactly right. Then the sandbox ran the tests with every patch applied
on 16.0.0: &lt;strong&gt;3 passed, 1 failed&lt;/strong&gt;. Gemma had replaced &lt;code&gt;invoice.request(...)&lt;/code&gt; with &lt;code&gt;raw_request(...)&lt;/code&gt;,
which returns a raw &lt;code&gt;StripeResponse&lt;/code&gt;, so &lt;code&gt;sent.id&lt;/code&gt; blew up. The recommendation is labelled
&lt;strong&gt;"Verified: failed"&lt;/strong&gt;, and nothing is applied: approving a patch only records the decision.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Follow-up:&lt;/strong&gt; I asked "Which file breaks first if we upgrade without any patch?" Backboard retrieved
the investigation's memory, and Gemma answered that the context doesn't say. It declined to make up an
ordering, and the UI shows the one memory it used.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Provenance:&lt;/strong&gt; a Sentry trace with &lt;strong&gt;315 spans&lt;/strong&gt; (version comparison 2.8 min, assessment 1.3 min,
patch proposal 7.4 min on Google's free tier), an Entire checkpoint linked to the migration agent's
commit, and the Temporal workflow and run IDs. All are linked from the investigation page.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Permissions:&lt;/strong&gt; on Settings → Security, the migration agent asking to &lt;code&gt;push_branch&lt;/code&gt; is &lt;strong&gt;denied&lt;/strong&gt;
(&lt;code&gt;repo:write&lt;/code&gt; missing), and &lt;code&gt;propose_patch&lt;/code&gt; is &lt;strong&gt;allowed&lt;/strong&gt;. Both use real Auth0 tokens.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;One flaw I'm leaving visible: the model-written &lt;em&gt;summary&lt;/em&gt; mentions a &lt;code&gt;KeyError&lt;/code&gt; that no test produced. The&lt;br&gt;
verdicts come from deterministic evidence, but the narrative is still model text, so the page labels it as&lt;br&gt;
such.&lt;/p&gt;
&lt;h2&gt;
  
  
  Code
&lt;/h2&gt;


&lt;div class="ltag-github-readme-tag"&gt;
  &lt;div class="readme-overview"&gt;
    &lt;h2&gt;
      &lt;img src="https://assets.dev.to/assets/github-logo-5a155e1f9a670af7944dd5e12375bc76ed542ea80224905ecaf878b9157cdefc.svg" alt="GitHub logo"&gt;
      &lt;a href="https://github.com/shaileshvats" rel="noopener noreferrer"&gt;
        shaileshvats
      &lt;/a&gt; / &lt;a href="https://github.com/shaileshvats/vendorwake" rel="noopener noreferrer"&gt;
        vendorwake
      &lt;/a&gt;
    &lt;/h2&gt;
    &lt;h3&gt;
      Open-source, open-weight AI dependency intelligence: detects upstream vendor changes and maps them to your code with evidence.
    &lt;/h3&gt;
  &lt;/div&gt;
  &lt;div class="ltag-github-body"&gt;
    
&lt;div id="readme" class="md"&gt;&lt;div class="markdown-heading"&gt;
&lt;h1 class="heading-element"&gt;Vendorwake&lt;/h1&gt;
&lt;/div&gt;
&lt;p&gt;&lt;strong&gt;The upstream changed. We caught it.&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;Vendorwake is an open-source, open-weight-AI dependency intelligence platform. It watches the vendors
APIs and SDKs your software depends on, detects meaningful upstream changes, and maps each one to the code
in your repository that it could affect. Every finding is labelled &lt;strong&gt;confirmed&lt;/strong&gt;, &lt;strong&gt;potential&lt;/strong&gt; or
&lt;strong&gt;unaffected&lt;/strong&gt;, and backed by evidence you can inspect.&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;Live demo:&lt;/strong&gt; &lt;a href="https://vendorwake-web.onrender.com" rel="nofollow noopener noreferrer"&gt;https://vendorwake-web.onrender.com&lt;/a&gt; (free Render tier; the first request after a quiet
period takes about a minute) · &lt;strong&gt;API docs:&lt;/strong&gt; &lt;a href="https://vendorwake-api.onrender.com/api/docs" rel="nofollow noopener noreferrer"&gt;https://vendorwake-api.onrender.com/api/docs&lt;/a&gt; ·
&lt;strong&gt;Write-up:&lt;/strong&gt; &lt;a href="https://dev.to/shaileshvats2004/vendorwake-the-upstream-changed-gemma-caught-it-and-a-test-proved-it-3o3f" rel="nofollow"&gt;the DEV post&lt;/a&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Status: working end to end on free tiers. The hosted demo investigates a real upstream change
stripe-python 15.6.1 → 16.0.0, against &lt;a href="https://github.com/shaileshvats/vendorwake/fixtures/stripe-billing-demo" rel="noopener noreferrer"&gt;a small billing fixture&lt;/a&gt;: three
files confirmed by a test that passes on 15.6.1 and fails on 16.0.0, one file unaffected, and proposed
patches that are re-tested in a sandbox (one of Gemma's patches fails, and the page says so).&lt;/p&gt;
&lt;/blockquote&gt;
&lt;div class="markdown-heading"&gt;
&lt;h2 class="heading-element"&gt;How&lt;/h2&gt;…&lt;/div&gt;&lt;/div&gt;
  &lt;/div&gt;
  &lt;div class="gh-btn-container"&gt;&lt;a class="gh-btn" href="https://github.com/shaileshvats/vendorwake" rel="noopener noreferrer"&gt;View on GitHub&lt;/a&gt;&lt;/div&gt;
&lt;/div&gt;


&lt;p&gt;Apache-2.0. FastAPI + Temporal + PostgreSQL/TimescaleDB/pgvector + Next.js, with an adapter per sponsor so&lt;br&gt;
the business logic never imports a vendor SDK.&lt;/p&gt;

&lt;h2&gt;
  
  
  Prize Categories
&lt;/h2&gt;

&lt;p&gt;I'm entering ten categories. Each sponsor does a real job in the hosted run above, and this is where to&lt;br&gt;
check it.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of Gemma:&lt;/strong&gt; Gemma 4 (&lt;code&gt;gemma-4-31b-it&lt;/code&gt;, falling back to &lt;code&gt;gemma-4-26b-a4b-it&lt;/code&gt;) does every
model step: extraction, impact rationale, the evidence graph, patches and follow-up answers. It runs on
Google AI Studio's free tier through an OpenAI-compatible adapter, so pointing it at vLLM or Ollama is a
config change.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of Render:&lt;/strong&gt; the whole app runs on Render's free tier. One service is the Next.js front end;
the other is the API container that runs the agents, the Temporal worker and the test sandbox.
&lt;code&gt;scripts/deploy_render.py&lt;/code&gt; creates both services and their settings through Render's API.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of Auth0 for AI Agents:&lt;/strong&gt; users sign in with Auth0, and each agent (discovery, repository,
impact, verification, migration) has its own machine identity with only the scopes its steps need.
Every tool call is checked against that agent's real token, so the migration agent's &lt;code&gt;push_branch&lt;/code&gt; is
denied and &lt;code&gt;propose_patch&lt;/code&gt; is allowed. Approving a patch is a human step, done in-app because Auth0's
async approval isn't on the free plan.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of Backboard:&lt;/strong&gt; memory and retrieval for an open-source assistant. Backboard stores each
investigation's findings and retrieves the relevant ones for a follow-up question; Gemma answers only
from what came back, and the UI lists the memories it used.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of Browserbase:&lt;/strong&gt; when a vendor's docs page is a JavaScript shell, a real Browserbase session
renders it. The session ID is kept as evidence next to the text Gemma reasons over.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of Entire:&lt;/strong&gt; the migration agent's work on each investigation is recorded as an Entire
session (each model turn with its token counts, then a commit of the proposed patches), and the
checkpoint is linked from the investigation page, so you can see why a patch exists.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of Sentry Agent Tracing:&lt;/strong&gt; each investigation is one trace, with a &lt;code&gt;gen_ai.invoke_agent&lt;/code&gt; span
per agent and &lt;code&gt;chat&lt;/code&gt; / &lt;code&gt;execute_tool&lt;/code&gt; spans under it carrying the model, provider and token counts.
The demo run's trace has 315 spans. Patch proposal took longest (7.4 min) because the adapter paces
Gemma calls to the free tier's 16K tokens per minute; version comparison (2.8 min) is installing two
Stripe versions and running the tests. Model cost: $0. Prompt text is never attached. Debugging it
taught me something too (below): my first trace check found zero spans.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of SerpApi:&lt;/strong&gt; live search for each vendor's release announcements. A result only points
Vendorwake at a page; it then fetches the text itself from the vendor's official domains, so a search
hit is never treated as proof.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of Temporal:&lt;/strong&gt; analysis, discovery, investigation and verification are Temporal workflows.
Each step saves its output before returning, so a restarted worker carries on without calling the model
again. When Google's free tier answers 429, the activity retries after the delay Google asks for
instead of failing the investigation, as my first runs did.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Best Use of Tiger Data:&lt;/strong&gt; Postgres on Tiger Cloud. Every fetched vendor page is a row in a
TimescaleDB hypertable, hashed so unchanged pages are skipped. Row-level security is forced on every
tenant table and keyed to the signed-in user. pgvector stores open-weight &lt;code&gt;bge-small&lt;/code&gt; embeddings for
"related past changes" (switched off on the hosted demo; see below).&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  How I Built It
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Deterministic code builds the evidence; the open-weight model interprets it.&lt;/strong&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Discovery.&lt;/strong&gt; SerpApi finds candidate announcements. A search hit is &lt;em&gt;never&lt;/em&gt; proof: Vendorwake only
trusts text it fetched itself from the vendor's official domains. It uses plain HTTP first and a
Browserbase browser when the page is a JavaScript shell. Each fetch is hashed and stored in a
TimescaleDB hypertable, so unchanged pages are skipped and every finding points at the exact bytes
it came from.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Extraction.&lt;/strong&gt; Gemma 4 turns a release section into structured changes: type, severity, affected
symbols, replacement and a verbatim evidence quote. Then a &lt;strong&gt;grounding check&lt;/strong&gt; throws out any quote that
isn't literally in the source. Vendor text is wrapped as untrusted data, and a planted "ignore previous
instructions" line in the tests gets flagged instead of obeyed.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Repository analysis.&lt;/strong&gt; Manifest parsers plus a Python AST scanner find imports, attribute chains like
&lt;code&gt;stripe.Reversal&lt;/code&gt;, and keyword calls like &lt;code&gt;.retrieve(customer=...)&lt;/code&gt;, each with a file and line.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Impact.&lt;/strong&gt; Rules match extracted symbols to code references and version ranges. Gemma writes the
rationale and builds an &lt;strong&gt;evidence graph&lt;/strong&gt; (vendor source → change → symbol → file → test) where every
edge points at a piece of evidence.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Migration and verification.&lt;/strong&gt; Gemma proposes a unified diff per affected file. Vendorwake checks that
the diff applies, then runs the fixture's tests in a fresh virtualenv before the upgrade, after it, and
after the patch. Patches are never pushed: no agent identity holds &lt;code&gt;repo:write&lt;/code&gt;.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;Things that surprised me while building on free plans only:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;OpenRouter's free Gemma pool was rate-limited upstream, so I moved to Google AI Studio's free tier.
Gemma 4 there always thinks before answering and rejects a thinking budget, so the adapter strips the
&lt;code&gt;&amp;lt;thought&amp;gt;&lt;/code&gt; block before validating.&lt;/li&gt;
&lt;li&gt;Backboard's free credit covers memory and retrieval but not chat. So Backboard stores and retrieves,
and Gemma writes the answer from exactly what was retrieved. Honestly, I like that split better.&lt;/li&gt;
&lt;li&gt;sentry-sdk 2.73 sends gen_ai spans as a separate span-streaming envelope, not inside
&lt;code&gt;transaction.spans&lt;/code&gt;. My first trace assertion found zero spans.&lt;/li&gt;
&lt;li&gt;Entire 0.12 stores checkpoints as git refs (&lt;code&gt;refs/entire/checkpoints/...&lt;/code&gt;) with 26-character IDs, which
differs from the docs I started from.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;What isn't done yet (said plainly):&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;GitHub access uses a read-only token, not Auth0 Token Vault. Auth0's async approval (CIBA) isn't on the
free plan, so approvals are in-app.&lt;/li&gt;
&lt;li&gt;Verification runs only for allow-listed repos, and on free hosting the sandbox can't fully cut network
access. The environment string on every result says so.&lt;/li&gt;
&lt;li&gt;On free Render, Temporal runs embedded and loses its history when the service sleeps or redeploys.
Reports and timelines live in Postgres, but an investigation that was mid-flight during a redeploy stays
stuck at "running".&lt;/li&gt;
&lt;li&gt;The 512 MB free instance can't also hold the ONNX embedding model, which got the container OOM-killed
once. So "related past changes" (pgvector) runs locally, and is switched off on the hosted demo.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Related reading on DEV:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://dev.to/getversyka/breaking-api-changes-turned-into-tested-pull-requests-4o80"&gt;Breaking API changes, turned into tested pull requests&lt;/a&gt;
by getversyka tackles the same pain from the pull-request side. Vendorwake's angle is the evidence
labels and an open-weight model.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://dev.to/hexisteme/how-to-make-an-ai-research-agent-label-facts-vs-inferences-a-deterministic-provenance-pipeline-5dfn"&gt;How to make an AI research agent label facts vs inferences — a deterministic provenance pipeline&lt;/a&gt;
by hexisteme argues for the same split: the LLM extracts, deterministic code decides what counts as a fact.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://dev.to/vivantejani/connected-is-not-proven-building-an-evidence-graph-that-admits-what-it-doesnt-know-4de5"&gt;Connected Is Not Proven: Building an Evidence Graph That Admits What It Doesn't Know&lt;/a&gt;
by vivantejani is the right instinct for evidence graphs: an edge needs a quote behind it.&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Why Open Innovation Matters
&lt;/h2&gt;

&lt;p&gt;A tool that reads untrusted vendor text and makes claims about my code has to be inspectable end to end:&lt;br&gt;
the model weights, the prompts, the rules that decide "confirmed", and the evidence behind each claim. With&lt;br&gt;
an open-weight model behind a plain adapter, nobody's API decides what my dependency watcher can see, and&lt;br&gt;
anyone can rerun the same investigation and get the same evidence.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Lazy Payoff
&lt;/h2&gt;

&lt;p&gt;I stopped reading changelogs. Vendorwake reads them, ignores the ones that don't touch my code, and opens&lt;br&gt;
the ones that do with the file, the line, the failing test and a proposed patch that has already been tested.&lt;/p&gt;

&lt;p&gt;For the Stripe upgrade, that work by hand would mean reading a 41-change release, grepping four files,&lt;br&gt;
setting up two virtualenvs, running the tests on both versions, writing patches and testing them again.&lt;br&gt;
Vendorwake did it in about 13 minutes while I wasn't watching, on free tiers. My part was reading one&lt;br&gt;
page and deciding whether to approve.&lt;/p&gt;

</description>
      <category>devchallenge</category>
      <category>hf26challenge</category>
      <category>opensource</category>
      <category>ai</category>
    </item>
  </channel>
</rss>
