<?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: krishna kapoor</title>
    <description>The latest articles on DEV Community by krishna kapoor (@krishnakapoor612).</description>
    <link>https://dev.to/krishnakapoor612</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F4192699%2F3403c62e-f28d-4e91-91bc-4153544247b3.png</url>
      <title>DEV Community: krishna kapoor</title>
      <link>https://dev.to/krishnakapoor612</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/krishnakapoor612"/>
    <language>en</language>
    <item>
      <title>Building GraphGuard: How a Graph Database Transformed Cybersecurity Investigation</title>
      <dc:creator>krishna kapoor</dc:creator>
      <pubDate>Sun, 18 Oct 2026 22:01:01 +0000</pubDate>
      <link>https://dev.to/krishnakapoor612/building-graphguard-how-a-graph-database-transformed-cybersecurity-investigation-d49</link>
      <guid>https://dev.to/krishnakapoor612/building-graphguard-how-a-graph-database-transformed-cybersecurity-investigation-d49</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;"Every alert has a story. Follow the graph to find it."&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;




&lt;p&gt;&lt;strong&gt;Live Demo Video:&lt;/strong&gt; &lt;a href="https://youtu.be/UB7seRPO52Y" rel="noopener noreferrer"&gt;https://youtu.be/UB7seRPO52Y&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Source Code:&lt;/strong&gt;  &lt;a href="https://github.com/KrishnaKapoor612/GraphGuard" rel="noopener noreferrer"&gt;https://github.com/KrishnaKapoor612/GraphGuard&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  Agents That Act on Connected Data
&lt;/h2&gt;




&lt;p&gt;&lt;strong&gt;&lt;em&gt;1. The Crisis in the SOC:&lt;/em&gt;&lt;/strong&gt; Alert Fatigue and Disconnected Dots&lt;br&gt;
Modern Security Operations Centers (SOCs) are drowning. A standard enterprise security stack generates thousands of alerts every single day: firewall drops, endpoint triggers, authentication anomalies, and DNS spikes.&lt;/p&gt;

&lt;p&gt;The industry refers to this as Alert Fatigue. But the real issue isn't just volume—it's lack of context.&lt;/p&gt;

&lt;p&gt;In traditional Security Information and Event Management (SIEM) tools, alerts arrive as isolated tabular records:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Alert ID: A-104&lt;br&gt;
Title: Suspicious Outbound Connection to Known Tor Exit Node&lt;br&gt;
Severity: CRITICAL | Status: OPEN | Device: WORKSTATION-07&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;A tier-1 security analyst looking at this single entry might think: "It's an outbound connection on port 443. Could be a developer using a privacy proxy. Let's close it or put it on low priority."&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;What the analyst cannot see is that:&lt;/u&gt;&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;WORKSTATION-07 is operated by Marcus Chen (an engineering user flagged with an elevated risk level).&lt;br&gt;
&lt;strong&gt;The exact same machine initiated an internal port scan across subnet 10.0.0.0/24 (Alert A-105) just 84 minutes earlier.&lt;br&gt;
The destination IP 185.220.101.45 is linked to active Command-and-Control (C2) beaconing (Alert A-106).&lt;/strong&gt;&lt;br&gt;
Both alerts are part of an ongoing attack campaign (Incident INC-001: Data Exfiltration Campaign).&lt;br&gt;
That incident directly threatens the organization's Payment Processing Service (SVC-001, Criticality: CRITICAL) and HR Portal (SVC-002, Criticality: HIGH).&lt;br&gt;
In relational databases and document stores, discovering this requires 5 recursive SQL JOINs or complex log correlation queries that analysts simply don't have time to write under pressure.&lt;/p&gt;

&lt;p&gt;Security data is not a flat spreadsheet. Security data is inherently a graph.&lt;/p&gt;


&lt;h2&gt;
  
  
  2. Our Hero: FalkorDB
&lt;/h2&gt;

&lt;p&gt;To bridge this gap, an AI agent cannot just rely on vector similarity or prompt engineering—it needs a high-performance, graph-native backbone.&lt;/p&gt;

&lt;p&gt;Enter FalkorDB.&lt;/p&gt;

&lt;p&gt;FalkorDB serves as the authoritative, central store for GraphGuard's connected security knowledge. In our prototype, FalkorDB does not merely power a pretty frontend diagram; it is the computational brain that transforms disjointed security events into an interconnected graph.&lt;/p&gt;


&lt;h2&gt;
  
  
  Why FalkorDB is Essential to GraphGuard:
&lt;/h2&gt;



&lt;p&gt;&lt;strong&gt;&lt;em&gt;Graph Traversal&lt;/em&gt;&lt;/strong&gt;: In an investigation, the AI agent makes 5 to 7 sequential queries to discover neighbors and trace attack paths. FalkorDB’s C-based, Redis-compatible graph architecture delivers sub-10ms query execution times, making the AI investigation feel instantaneous and responsive.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;Expressive OpenCypher Engine:&lt;/em&gt;&lt;/strong&gt; Complex multi-hop relationships that require paragraphs of code in relational or document databases are queried in a few lines of declarative Cypher.&lt;br&gt;
Idempotency with MERGE: Security environments require repeatable demos and reliable pipelines. FalkorDB's full support for MERGE ensures that our synthetic seed scripts and recurring incident logs update relationships without creating duplicate entities.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;Persistent Agent Memory Across Sessions:&lt;/em&gt;&lt;/strong&gt; Unlike stateless LLM chatbots that lose context once a browser closes, GraphGuard persists completed investigations and derived evidence as first-class Investigation and Evidence nodes directly in FalkorDB. On future sessions, the agent queries past investigations using graph patterns.&lt;/p&gt;


&lt;h2&gt;
  
  
  3. The Graph Data Model
&lt;/h2&gt;



&lt;p&gt;&lt;strong&gt;GraphGuard&lt;/strong&gt; models cybersecurity operations as a property graph with 8 node labels and 10 relationship types:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;Nodes:&lt;/em&gt;&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;User (id, name, department, role, risk_level)&lt;/li&gt;
&lt;li&gt;Device (id, hostname, device_type, status, last_seen)&lt;/li&gt;
&lt;li&gt;IPAddress (id, address, reputation, country)&lt;/li&gt;
&lt;li&gt;Alert (id, title, severity, category, timestamp, status, description)&lt;/li&gt;
&lt;li&gt;Incident (id, title, severity, status, created_at)&lt;/li&gt;
&lt;li&gt;Service (id, name, criticality, owner_team)&lt;/li&gt;
&lt;li&gt;Investigation (id, question, summary, created_at, outcome, severity_assessment)&lt;/li&gt;
&lt;li&gt;Evidence (id, source_type, description, observed_at)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Graph Relationships:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;(User)-[:USES]-&amp;gt;(Device)&lt;/li&gt;
&lt;li&gt;(Device)-[:CONTACTED]-&amp;gt;(IPAddress)&lt;/li&gt;
&lt;li&gt;(Device)-[:TRIGGERED]-&amp;gt;(Alert)&lt;/li&gt;
&lt;li&gt;(IPAddress)-[:ASSOCIATED_WITH]-&amp;gt;(Alert)&lt;/li&gt;
&lt;li&gt;(Alert)-[:PART_OF]-&amp;gt;(Incident)&lt;/li&gt;
&lt;li&gt;(Incident)-[:AFFECTS]-&amp;gt;(Service)&lt;/li&gt;
&lt;li&gt;(User)-[:INVOLVED_IN]-&amp;gt;(Incident)&lt;/li&gt;
&lt;li&gt;(Investigation)-[:EXAMINED]-&amp;gt;(Alert)&lt;/li&gt;
&lt;li&gt;(Investigation)-[:USED_EVIDENCE]-&amp;gt;(Evidence)&lt;/li&gt;
&lt;li&gt;(Evidence)-[:SUPPORTS]-&amp;gt;(Incident)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The database comes pre-seeded with 27 base entities and 28 relationships representing 3 realistic scenarios:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;Scenario A (Multi-Hop Compromise Chain)&lt;/u&gt;&lt;/strong&gt;: Alert A-104 linking Marcus Chen, WORKSTATION-07, Tor IP 185.220.101.45, Incident INC-001, and the Payment Processing Service.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;Scenario B (Finance Credential Attack)&lt;/u&gt;&lt;/strong&gt;: Ryan Patel, LAPTOP-45, suspicious IP 192.0.2.99, failed logins Alert A-301, and Incident INC-002 affecting the Internal Finance System.&lt;br&gt;
Scenario C (Benign Baseline): Alice Thompson, LAPTOP-22, Google DNS 8.8.8.8, and false-positive Alert A-201 (proving the AI doesn't flag everything as malicious).&lt;/p&gt;


&lt;h2&gt;
  
  
  4. Cypher in Action: The Core Queries
&lt;/h2&gt;



&lt;p&gt;GraphGuard uses a centralized library of over 20 parameterized Cypher queries. Here are the three queries that drive the investigation engine:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;1. Tracing the 4-Hop Attack Path (TRACE_INCIDENT_PATH)&lt;br&gt;
&lt;/u&gt;&lt;/strong&gt;&lt;br&gt;
When an analyst selects an alert, this single query traverses out 4 hops to map devices, contacted IPs, related alerts, incidents, and endangered critical services:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight cypher"&gt;&lt;code&gt;&lt;span class="k"&gt;MATCH&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;a:&lt;/span&gt;&lt;span class="n"&gt;Alert&lt;/span&gt; &lt;span class="ss"&gt;{&lt;/span&gt;&lt;span class="py"&gt;id:&lt;/span&gt; &lt;span class="n"&gt;$alert_id&lt;/span&gt;&lt;span class="ss"&gt;})&lt;/span&gt;
&lt;span class="k"&gt;OPTIONAL&lt;/span&gt; &lt;span class="k"&gt;MATCH&lt;/span&gt; &lt;span class="n"&gt;path1&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;d:&lt;/span&gt;&lt;span class="n"&gt;Device&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:TRIGGERED&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;OPTIONAL&lt;/span&gt; &lt;span class="k"&gt;MATCH&lt;/span&gt; &lt;span class="n"&gt;path2&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;u:&lt;/span&gt;&lt;span class="n"&gt;User&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:USES&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;OPTIONAL&lt;/span&gt; &lt;span class="k"&gt;MATCH&lt;/span&gt; &lt;span class="n"&gt;path3&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:CONTACTED&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;ip:&lt;/span&gt;&lt;span class="n"&gt;IPAddress&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;OPTIONAL&lt;/span&gt; &lt;span class="k"&gt;MATCH&lt;/span&gt; &lt;span class="n"&gt;path4&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ip&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:ASSOCIATED_WITH&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;related_a:&lt;/span&gt;&lt;span class="n"&gt;Alert&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;OPTIONAL&lt;/span&gt; &lt;span class="k"&gt;MATCH&lt;/span&gt; &lt;span class="n"&gt;path5&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:PART_OF&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;inc:&lt;/span&gt;&lt;span class="n"&gt;Incident&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;OPTIONAL&lt;/span&gt; &lt;span class="k"&gt;MATCH&lt;/span&gt; &lt;span class="n"&gt;path6&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="n"&gt;inc&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:AFFECTS&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;svc:&lt;/span&gt;&lt;span class="n"&gt;Service&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;OPTIONAL&lt;/span&gt; &lt;span class="k"&gt;MATCH&lt;/span&gt; &lt;span class="n"&gt;path7&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="n"&gt;u&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:INVOLVED_IN&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="n"&gt;inc&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;RETURN&lt;/span&gt;
    &lt;span class="n"&gt;a.id&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;start_alert_id&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;a.title&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;start_alert_title&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;d.hostname&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;hostname&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;u.name&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;user_name&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;u.risk_level&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;user_risk_level&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;ip.address&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;ip_address&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;ip.reputation&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;ip_reputation&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;related_a.id&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;related_alert_id&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;related_a.title&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;related_alert_title&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;inc.id&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;incident_id&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;inc.title&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;incident_title&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;svc.name&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;service_name&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;svc.criticality&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;service_criticality&lt;/span&gt;

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

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;u&gt;2. Discovering Hidden Pivot Connections (FIND_RELATED_ALERTS_VIA_IP)&lt;br&gt;
&lt;/u&gt;&lt;/strong&gt;&lt;br&gt;
Often, two alerts seem unrelated because they occurred at different times on different endpoints. By pivoting through the contacted IP address, FalkorDB uncovers the hidden link:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight cypher"&gt;&lt;code&gt;&lt;span class="k"&gt;MATCH&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;a:&lt;/span&gt;&lt;span class="n"&gt;Alert&lt;/span&gt; &lt;span class="ss"&gt;{&lt;/span&gt;&lt;span class="py"&gt;id:&lt;/span&gt; &lt;span class="n"&gt;$alert_id&lt;/span&gt;&lt;span class="ss"&gt;})&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:TRIGGERED&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;d:&lt;/span&gt;&lt;span class="n"&gt;Device&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:CONTACTED&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;ip:&lt;/span&gt;&lt;span class="n"&gt;IPAddress&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="ss"&gt;[&lt;/span&gt;&lt;span class="nc"&gt;:ASSOCIATED_WITH&lt;/span&gt;&lt;span class="ss"&gt;]&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;other:&lt;/span&gt;&lt;span class="n"&gt;Alert&lt;/span&gt;&lt;span class="ss"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;other.id&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;$alert_id&lt;/span&gt;
&lt;span class="k"&gt;RETURN&lt;/span&gt;
    &lt;span class="n"&gt;other.id&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;alert_id&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;other.title&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;title&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;other.severity&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;severity&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;other.category&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;category&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;other.timestamp&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;timestamp&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;ip.address&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;via_ip&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;ip.reputation&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;ip_reputation&lt;/span&gt;
&lt;span class="k"&gt;LIMIT&lt;/span&gt; &lt;span class="n"&gt;$limit&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;u&gt;3. Persistent Cross-Session Memory (SAVE_INVESTIGATION)&lt;br&gt;
&lt;/u&gt;&lt;/strong&gt;&lt;br&gt;
When an investigation concludes, findings are committed to FalkorDB so any analyst can resume the investigation tomorrow:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight cypher"&gt;&lt;code&gt;&lt;span class="k"&gt;MERGE&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="ss"&gt;(&lt;/span&gt;&lt;span class="py"&gt;inv:&lt;/span&gt;&lt;span class="n"&gt;Investigation&lt;/span&gt; &lt;span class="ss"&gt;{&lt;/span&gt;&lt;span class="py"&gt;id:&lt;/span&gt; &lt;span class="n"&gt;$inv_id&lt;/span&gt;&lt;span class="ss"&gt;})&lt;/span&gt;
&lt;span class="k"&gt;SET&lt;/span&gt; &lt;span class="n"&gt;inv.question&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;$question&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;inv.summary&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;$summary&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;inv.created_at&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;$created_at&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;inv.outcome&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;$outcome&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;inv.recommended_steps&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;$recommended_steps&lt;/span&gt;&lt;span class="ss"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;inv.severity_assessment&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;$severity_assessment&lt;/span&gt;
&lt;span class="k"&gt;RETURN&lt;/span&gt; &lt;span class="n"&gt;inv.id&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  5. Our Solution: GraphGuard
&lt;/h2&gt;

&lt;p&gt;GraphGuard pairs FalkorDB with Google Gemini (gemini-3.8-flash) and LangChain to create an interactive investigation platform.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;
┌────────────────────────────────────────────────────────────────
│                   Streamlit Web Interface                       │
│     Overview  |  Investigate  |  Graph Explorer  |  History     │
└─────────────────────────────────┬──────────────────────────────
                                  │
┌─────────────────────────────────▼──────────────────────────────
│              Agent Service (Gemini + LangChain)                 │
│   7 Predefined Safe Tools — No Arbitrary Cypher Allowed         │
└─────────────────────────────────┬──────────────────────────────
                                  │
┌─────────────────────────────────▼──────────────────────────────
│          Graph &amp;amp; Investigation Service Layer                    │
│   Deterministic Orchestrator, Evidence Integrity, Memory        │
└─────────────────────────────────┬──────────────────────────────
                                  │
┌─────────────────────────────────▼──────────────────────────────
│                  FalkorDB Graph Database                        │
│   Nodes: Users, Devices, IPs, Alerts, Incidents, Services       │
└────────────────────────────────────────────────────────────────

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

&lt;/div&gt;



&lt;p&gt;Safety and Epistemic Integrity by Design&lt;br&gt;
A major pitfall in cybersecurity AI agents is "_hallucination under fire"—_an LLM hallucinating IP addresses or making unwarranted claims. GraphGuard solves this with strict guardrails:&lt;/p&gt;

&lt;p&gt;Predefined Safe Tool Registry: &lt;strong&gt;&lt;em&gt;The LLM is never given direct Cypher execution privileges. It can only call 7 structured tools (get_alert_details, investigate_device, find_related_alerts, trace_incident_path, get_affected_services, save_investigation, and get_previous_investigation).&lt;/em&gt;&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;Confirmed Facts vs. Inferences:&lt;/u&gt;&lt;/strong&gt; &lt;br&gt;
The user interface explicitly separates:&lt;/p&gt;

&lt;p&gt;✅ &lt;u&gt;&lt;strong&gt;Confirmed Facts&lt;/strong&gt;&lt;/u&gt;: Statements derived directly from verified Cypher query results (e.g., "WORKSTATION-07 connected to 185.220.101.45").&lt;/p&gt;

&lt;p&gt;🔶 &lt;strong&gt;&lt;u&gt;Inferences&lt;/u&gt;&lt;/strong&gt;: Hypotheses generated by the LLM, strictly prefixed with &lt;a href="//e.g.,"&gt;INFERRED&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;❓ &lt;strong&gt;&lt;u&gt;Unknowns&lt;/u&gt;&lt;/strong&gt;: Open questions the graph has not yet answered (e.g., "Whether credentials on WORKSTATION-07 were dumped from memory").&lt;/p&gt;

&lt;p&gt;&lt;em&gt;No Autonomous Destructive Actions: GraphGuard operates as a defensive decision-support system. All recommended actions include mandatory human-in-the-loop review.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;Deterministic Fallback Engine&lt;/u&gt;&lt;/strong&gt;: If the Gemini API key is missing or external APIs are unreachable, GraphGuard automatically falls back to its deterministic graph investigation orchestrator—ensuring SOC continuity without degradation.&lt;/p&gt;


&lt;h2&gt;
  
  
  6. The User Experience: 4 Intuitive Views
&lt;/h2&gt;



&lt;p&gt;Built with Streamlit &lt;strong&gt;GraphGuard&lt;/strong&gt; features four dedicated workspaces:&lt;/p&gt;

&lt;p&gt;📊&lt;em&gt;Overview Dashboard&lt;/em&gt;: Real-time FalkorDB metrics (live node and relationship counts, active incidents, alert severities, and system health status).&lt;/p&gt;

&lt;p&gt;🔍 &lt;em&gt;Investigation Workspace&lt;/em&gt;: The analyst selects an alert (e.g., A-104) or types an investigation question. Within seconds, GraphGuard queries FalkorDB, activates the Gemini agent, and outputs the full incident narrative, graph evidence path, related alerts, affected services, and defensive recommendations.&lt;/p&gt;

&lt;p&gt;🕸️ &lt;em&gt;Graph Explorer&lt;/em&gt;: An interactive 2D circular/force layout powered by Plotly. Analysts can visually inspect nodes (color-coded by type), click to view properties, and trace incoming and outgoing graph edges.&lt;/p&gt;

&lt;p&gt;📁 &lt;em&gt;Investigation History (Persistent Memory)&lt;/em&gt;: Demonstrates cross-session memory by querying past Investigation nodes stored in FalkorDB. Analysts can ask follow-up questions like "What did we find when we investigated alert A-104 earlier?" and review previous findings.&lt;/p&gt;
&lt;h2&gt;
  
  
  7. The Walkthrough: Investigating Alert A-104
&lt;/h2&gt;

&lt;p&gt;Here is the exact journey GraphGuard performs during a live investigation:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Alert A-104 (Outbound Tor)
        │
    [TRIGGERED]
        ▼
  WORKSTATION-07 ────────[USES]────────► Marcus Chen (HIGH Risk)
        │
  [CONTACTED]
        ▼
  185.220.101.45 (Tor Exit) ────[ASSOCIATED_WITH]────► Alert A-106 (C2 Beacon)
        │
    [PART_OF]
        ▼
  Incident INC-001 (Data Exfiltration)
        │
    [AFFECTS]
        ├────────► Payment Processing Service (CRITICAL)
        └────────► HR Employee Portal (HIGH)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;u&gt;Step 1&lt;/u&gt;&lt;/strong&gt;: The agent executes get_alert_details("A-104"). It discovers the alert originated from WORKSTATION-07.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;Step 2&lt;/u&gt;&lt;/strong&gt;: The agent calls investigate_device("D-001"). It reveals the device is used by senior developer Marcus Chen (high risk) and previously triggered A-105 (Internal Port Scan).&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;Step 3&lt;/u&gt;&lt;/strong&gt;: The agent executes trace_incident_path("A-104"). It follows the connection to IP 185.220.101.45 (reputation: malicious, active Tor exit in the Netherlands).&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;Step 4&lt;/u&gt;&lt;/strong&gt;: The agent pivots to find related alerts. It spots that 185.220.101.45 is also associated with Alert A-106: C2 Beacon Attempt.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;Step 5&lt;/u&gt;&lt;/strong&gt;: The path connects to Incident INC-001, which directly affects the Payment Processing Service.&lt;/p&gt;

&lt;p&gt;Step 6: GraphGuard saves the full investigation record to FalkorDB for future reference.&lt;br&gt;
&lt;em&gt;In less than 3 seconds, a low-priority outbound connection alert was upgraded to a verified, multi-stage data exfiltration campaign threatening financial infrastructure.&lt;/em&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  8. Why GraphGuard Must Be Adopted
&lt;/h2&gt;




&lt;p&gt;Solves the Disconnected Data Problem: Security attackers think in graphs; security defenders too often look at lists. GraphGuard levels the playing field by matching the attacker's connected mindset.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Reduces Mean Time to Detect and Respond (MTTD / MTTR): Instead of manually cross-referencing IP blacklists, endpoint logs, and active directory hierarchies across 4 browser tabs, an analyst gets the full connected context in a single query.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Eliminates AI Hallucinations in High-Stakes Environments: By anchoring the agent to real Cypher query outputs and enforcing fact-versus-inference separation, analysts can trust the recommendations.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Continuous Institutional Memory: Turnover in SOC teams often leads to lost investigation context. Persisting investigations in FalkorDB builds an organizational graph brain that gets smarter with every incident investigated.&lt;/strong&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  9. Key Learnings &amp;amp; Engineering Reflections
&lt;/h2&gt;




&lt;p&gt;Building GraphGuard reinforced several crucial software and architectural lessons:&lt;/p&gt;

&lt;p&gt;Graph databases are natural context engines for LLMs: Giving an LLM raw documents or flat tables forces it to guess relationships. Giving an LLM a graph database allows it to traverse explicit, verified relationships with surgical precision.&lt;br&gt;
Constrained agency builds robust software: Unrestricted AI agents running arbitrary Cypher are dangerous in production. Restricting the agent to deterministic, parameterized query tools produced 100% reliable results while preventing injection risks.&lt;br&gt;
Idempotency is king: Designing the seed scripts with Cypher MERGE clauses saved hours of reset time and ensured our 14 automated unit tests ran reliably.&lt;/p&gt;




&lt;h2&gt;
  
  
  10. Verification &amp;amp; Code Quality
&lt;/h2&gt;




&lt;p&gt;GraphGuard isn't a mock-up—it is an end-to-end, tested prototype:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;14 Unit Tests Passing&lt;/u&gt;&lt;/strong&gt;: Covering configuration security, Cypher query formatting, deterministic orchestration, and schema validation.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;u&gt;Automated Health Check (6/6 Passing)&lt;/u&gt;&lt;/strong&gt;: Verifying live cloud database connection, seed data completeness, multi-hop query resolution, and Gemini API availability.&lt;br&gt;
Check Out the Project!&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Live Demo Video:&lt;/strong&gt; &lt;a href="https://youtu.be/UB7seRPO52Y" rel="noopener noreferrer"&gt;https://youtu.be/UB7seRPO52Y&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Source Code:&lt;/strong&gt;  &lt;a href="https://github.com/KrishnaKapoor612/GraphGuard" rel="noopener noreferrer"&gt;https://github.com/KrishnaKapoor612/GraphGuard&lt;/a&gt;&lt;br&gt;
&lt;strong&gt;Built for: Graph Hacks 2026: Track 1 — Agents That Act on Connected Data&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;If you enjoyed this writeup, please give the GitHub repository a &lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;** star** and share your thoughts in the comments below!&lt;/p&gt;
&lt;/blockquote&gt;

</description>
      <category>langchain</category>
      <category>agents</category>
      <category>falkordb</category>
      <category>ai</category>
    </item>
  </channel>
</rss>
