<?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: Valery Odinga</title>
    <description>The latest articles on DEV Community by Valery Odinga (@odingaval).</description>
    <link>https://dev.to/odingaval</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F3269806%2F95be98b3-c723-4708-b388-f66b73977499.jpg</url>
      <title>DEV Community: Valery Odinga</title>
      <link>https://dev.to/odingaval</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/odingaval"/>
    <language>en</language>
    <item>
      <title>Trust, but Verify: Fighting Credential Fraud with Solana</title>
      <dc:creator>Valery Odinga</dc:creator>
      <pubDate>Tue, 02 Jun 2026 20:45:40 +0000</pubDate>
      <link>https://dev.to/odingaval/trust-but-verify-fighting-credential-fraud-with-solana-kl4</link>
      <guid>https://dev.to/odingaval/trust-but-verify-fighting-credential-fraud-with-solana-kl4</guid>
      <description>&lt;p&gt;A mother walked into a neighbourhood pharmacy and handed over a prescription for her sick child. The chemist reached for a bottle, dispensed the medicine with confidence, and told her how to apply it. She went home and did exactly what she was told.&lt;/p&gt;

&lt;p&gt;The medicine was wrong. It was meant for adult dermatological use. Applied to a child's eyes, the damage was irreversible.&lt;/p&gt;

&lt;p&gt;The chemist wasn't necessarily malicious. But something had failed long before that counter interaction, there was no easy way to verify that this person was actually qualified to dispense prescription medicine. No quick check. No public record a patient could pull up on their phone before handing over trust.&lt;/p&gt;

&lt;p&gt;We check Yelp reviews before visiting a restaurant. We check ratings before getting into an Uber. But the pharmacist who handles our prescriptions, the electrician wiring our home, the contractor managing our building, for these we largely take their word for it, or at best call a licensing board that might or might not pick up.&lt;/p&gt;

&lt;p&gt;That bothered us. And it led our group to start building Veryfy.&lt;/p&gt;

&lt;p&gt;The Real Problem: Credentials Live in Silos&lt;br&gt;
Professional licenses, certifications, and service authorisations exist, but they're scattered. They live in government databases, PDF certificates pinned to office walls, or email attachments. To verify one, you either:&lt;/p&gt;

&lt;p&gt;Call an office that's open 9–5, or&lt;br&gt;
Trust a paper document that could have been printed this morning.&lt;br&gt;
The information asymmetry is staggering. The professional always knows exactly what their credentials say. The patient, the customer, the client, they're almost always flying blind.&lt;/p&gt;

&lt;p&gt;What if a license was something you could independently verify in seconds, from your phone, before you walked into that pharmacy? No phone call. No middleman. Just a hash, a blockchain, and a yes or no.&lt;/p&gt;

&lt;p&gt;That's the idea behind &lt;code&gt;Veryfy&lt;/code&gt;, a decentralised credential verification protocol we are currently developing.&lt;/p&gt;

&lt;p&gt;What &lt;code&gt;Veryfy&lt;/code&gt; Does&lt;br&gt;
&lt;code&gt;Veryfy&lt;/code&gt; is an on-chain license verification protocol built on Solana. In plain terms:&lt;/p&gt;

&lt;p&gt;An issuer (a licensing body, an institution, a platform) registers on-chain and issues a license tied to a specific credential or asset.&lt;br&gt;
That license is written to the blockchain permanently, publicly, and tamper-proof.&lt;br&gt;
Anyone:-  a patient, a customer, an auditor can verify that license instantly, without asking the issuer.&lt;br&gt;
No more "trust me, I'm licensed." The license speaks for itself.&lt;/p&gt;

&lt;p&gt;How It Works&lt;br&gt;
It's in three parts:&lt;/p&gt;

&lt;p&gt;The Blockchain Layer (the source of truth) Every license is stored as a record on the Solana blockchain. It holds: who issued it, who holds it, whether it's active or revoked, and when it expires. Once written, nobody, not even the issuer can quietly change it. Revoking a license creates a new public record, not a silent deletion.&lt;/p&gt;

&lt;p&gt;The API Layer (the bridge) A lightweight Go server handles the off-chain logic: hashing documents, validating requests, exposing clean HTTP endpoints. This is what a hospital system, a pharmacy app, or a government portal would integrate with.&lt;/p&gt;

&lt;p&gt;The Web App A React frontend gives issuers a dashboard to issue and revoke licenses, and gives anyone a public verification page scan the QR code, and instantly see if the license is real.&lt;/p&gt;

&lt;p&gt;A Peek Under the Hood&lt;br&gt;
If you're technical, here's the part that makes it work cleanly.&lt;/p&gt;

&lt;p&gt;Each license is stored as a Program Derived Address (PDA) on Solana- an account whose address is deterministically derived from the content it represents. Specifically, it's seeded by a 32-byte SHA-256 hash of the credential document:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight rust"&gt;&lt;code&gt;&lt;span class="n"&gt;rust&lt;/span&gt;
&lt;span class="n"&gt;seeds&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;b"license"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;asset_hash&lt;/span&gt;&lt;span class="nf"&gt;.as_ref&lt;/span&gt;&lt;span class="p"&gt;()]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;,&lt;br&gt;
This means: given any document, you can compute its hash and look up exactly one on-chain record no index, no search, no intermediary. The blockchain address is the lookup key.&lt;/p&gt;

&lt;p&gt;A license record looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight rust"&gt;&lt;code&gt;&lt;span class="n"&gt;rust&lt;/span&gt;
&lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt; &lt;span class="n"&gt;License&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="n"&gt;holder&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Pubkey&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;          &lt;span class="c1"&gt;// who holds the license&lt;/span&gt;
    &lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="n"&gt;issuer&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Pubkey&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;          &lt;span class="c1"&gt;// who issued it&lt;/span&gt;
    &lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;LicenseStatus&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;   &lt;span class="c1"&gt;// Active | Revoked | Expired&lt;/span&gt;
    &lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="n"&gt;expiry&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;i64&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;             &lt;span class="c1"&gt;// 0 = never expires&lt;/span&gt;
    &lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="n"&gt;asset_hash&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nb"&gt;u8&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="mi"&gt;32&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;   &lt;span class="c1"&gt;// the credential's fingerprint&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And only the registered issuer authority can revoke it enforced at the contract level, not just in application logic:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight rust"&gt;&lt;code&gt;&lt;span class="n"&gt;rust&lt;/span&gt;
&lt;span class="nd"&gt;#[account(&lt;/span&gt;
    &lt;span class="nd"&gt;has_one&lt;/span&gt; &lt;span class="nd"&gt;=&lt;/span&gt; &lt;span class="nd"&gt;authority&lt;/span&gt; &lt;span class="err"&gt;@&lt;/span&gt; &lt;span class="nd"&gt;VeryfyError::UnauthorizedIssuer,&lt;/span&gt;
&lt;span class="nd"&gt;)]&lt;/span&gt;
&lt;span class="k"&gt;pub&lt;/span&gt; &lt;span class="n"&gt;issuer&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Account&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nv"&gt;'info&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;Issuer&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Back to That Pharmacy&lt;br&gt;
Imagine this instead: the pharmacy's license is issued on-chain by the national pharmaceutical regulatory body. Before a patient enters, they scan a QR code on the door. The app hashes the pharmacy's registration document, looks it up on-chain, and returns:&lt;/p&gt;

&lt;p&gt;License Active - Issued by National Pharmacy Council- Valid until Dec 2026&lt;/p&gt;

&lt;p&gt;Or:&lt;/p&gt;

&lt;p&gt;License Revoked - Revocation recorded 14 March 2025&lt;/p&gt;

&lt;p&gt;No phone call. No trusting a certificate in a frame. Just a public, unforgeable record.&lt;/p&gt;

&lt;p&gt;That's not science fiction. The infrastructure to do this already exists. What's been missing is a standardised way to put credentials on-chain and make verification dead simple.&lt;br&gt;
Trust, but Verify: Fighting Credential Fraud with Solana&lt;/p&gt;

&lt;p&gt;Veryfy is currently under active development. We have built a functional prototype running on a local Solana validator with a connected React UI and Go API, but we are working hard to expand it. Our immediate roadmap includes:&lt;/p&gt;

&lt;p&gt;License Renewal - completing the on-chain implementation for extending license validity.&lt;br&gt;
QR Code Verification Flow - so the pharmacy-door scenario above is a real UX, not just a thought experiment.&lt;br&gt;
Institutional Integrations - working with licensing bodies to pilot real credential issuance.&lt;br&gt;
Try It / Contribute&lt;br&gt;
The full source code is open on GitHub: github.com/odingaval/veryfy.git&lt;/p&gt;

&lt;p&gt;Since Veryfy is actively under development, we welcome contributions! The stack is Rust (Anchor), Go, and React/TypeScript - if any of those are your world, we would love to have you collaborate with us.&lt;/p&gt;

&lt;p&gt;And if you've ever been on the wrong side of an unverifiable credential as a patient, a customer, or someone who's had to just hope the person helping them was who they said they were, we'd genuinely like to hear your story in the comments. That's the problem we are trying to solve.&lt;/p&gt;

</description>
      <category>blockchain</category>
      <category>cybersecurity</category>
      <category>security</category>
      <category>web3</category>
    </item>
    <item>
      <title>Building Cursor for Community: A Buildathon Built on Time Pressure</title>
      <dc:creator>Valery Odinga</dc:creator>
      <pubDate>Mon, 25 May 2026 17:26:08 +0000</pubDate>
      <link>https://dev.to/odingaval/building-cursor-for-community-a-buildathon-built-on-time-pressure-12ih</link>
      <guid>https://dev.to/odingaval/building-cursor-for-community-a-buildathon-built-on-time-pressure-12ih</guid>
      <description>&lt;p&gt;Over the weekend, I attended an event hosted by &lt;strong&gt;Cursor Kenya&lt;/strong&gt;, bringing together developers, builders, and tech enthusiasts to explore modern AI-assisted development workflows and collaboration tools.&lt;/p&gt;

&lt;p&gt;The sessions focused on how developers can build faster using AI, improve productivity, and rethink how software is developed in collaborative environments. We also got introduced to tools like &lt;strong&gt;Sentry&lt;/strong&gt; for monitoring and debugging applications, received credits to experiment with, and later moved into a &lt;strong&gt;buildathon&lt;/strong&gt; challenge.&lt;/p&gt;

&lt;p&gt;What followed was not just a coding exercise, but a very tight constraint problem: we had &lt;strong&gt;one hour to build a working prototype&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;That constraint became the foundation of everything we built.&lt;/p&gt;




&lt;h2&gt;
  
  
  The Reality of Hackathons and Time Constraints
&lt;/h2&gt;

&lt;p&gt;Anyone who has participated in hackathons or coding competitions knows that time is the most limiting resource.&lt;/p&gt;

&lt;p&gt;In theory, teams are supposed to:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;brainstorm ideas,&lt;/li&gt;
&lt;li&gt;design a solution,&lt;/li&gt;
&lt;li&gt;divide tasks,&lt;/li&gt;
&lt;li&gt;build a working prototype,&lt;/li&gt;
&lt;li&gt;and prepare a demo all within a few hours or days.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In reality, most of the time disappears into coordination.&lt;/p&gt;

&lt;p&gt;Even simple things like:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Who is working on what?&lt;/li&gt;
&lt;li&gt;Has this feature been pushed?&lt;/li&gt;
&lt;li&gt;Can someone review this?&lt;/li&gt;
&lt;li&gt;Where is the latest version?&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;…become friction points.&lt;/p&gt;

&lt;p&gt;And in fast-paced environments like hackathons, bootcamps, or team coding sessions, that friction slows everything down.&lt;/p&gt;

&lt;p&gt;During the buildathon, that limitation was very visible because the time window was extremely small, just &lt;strong&gt;60 minutes&lt;/strong&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  Where the Idea Started
&lt;/h2&gt;

&lt;p&gt;The idea for &lt;strong&gt;Cursor for Community&lt;/strong&gt; did not start as a product idea. It started as a response to the constraint.&lt;/p&gt;

&lt;p&gt;We quickly realized that if time is the biggest limitation, then anything that adds delay to collaboration becomes a problem.&lt;/p&gt;

&lt;p&gt;Most developer workflows rely heavily on:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;pushing code to GitHub,&lt;/li&gt;
&lt;li&gt;waiting for updates,&lt;/li&gt;
&lt;li&gt;reviewing changes after commits,&lt;/li&gt;
&lt;li&gt;and communicating separately through chat tools.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That works in normal development cycles, but not in time-bound environments.&lt;/p&gt;

&lt;p&gt;So instead of trying to optimize existing workflows, we asked a different question:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What if collaboration happened in real time, inside the coding environment itself?&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;That question became the foundation of the project.&lt;/p&gt;




&lt;h2&gt;
  
  
  Building Cursor for Community
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Cursor for Community&lt;/strong&gt; was designed as a collaboration platform for hackathons, bootcamps, and any environment where multiple developers build together under time pressure.&lt;/p&gt;

&lt;p&gt;The main goal was simple: reduce the delay between writing code and collaborating on it.&lt;/p&gt;

&lt;p&gt;Instead of waiting for commits or pull requests, developers could work in a shared space where progress is visible instantly.&lt;/p&gt;

&lt;p&gt;The system focused on three core ideas:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;real-time visibility,&lt;/li&gt;
&lt;li&gt;faster feedback loops,&lt;/li&gt;
&lt;li&gt;and reduced coordination overhead.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This allowed teams to stay focused on building rather than managing workflow transitions.&lt;/p&gt;




&lt;h2&gt;
  
  
  Real-Time Code Tracking
&lt;/h2&gt;

&lt;p&gt;One of the core features was &lt;strong&gt;live code tracking&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Instead of waiting for someone to push changes to GitHub, team members could join a shared workspace and see updates as they happened.&lt;/p&gt;

&lt;p&gt;This changed the collaboration model from:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;“push → wait → review”&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;to:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;“write → see → react”&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;This small shift significantly reduces the lag between development and feedback, especially in time-constrained environments like hackathons.&lt;/p&gt;

&lt;p&gt;It also makes it easier for teammates to stay aligned without constant status updates.&lt;/p&gt;




&lt;h2&gt;
  
  
  Team Chat for Fast Coordination
&lt;/h2&gt;

&lt;p&gt;To support collaboration, we added a &lt;strong&gt;team chat system&lt;/strong&gt; inside the platform.&lt;/p&gt;

&lt;p&gt;The goal was not to replace existing communication tools, but to keep communication close to the code.&lt;/p&gt;

&lt;p&gt;Instead of switching between messaging apps and code editors, teams could:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;ask questions,&lt;/li&gt;
&lt;li&gt;coordinate tasks,&lt;/li&gt;
&lt;li&gt;and resolve blockers quickly in the same environment.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This reduced context switching, which is often one of the biggest productivity killers in fast-paced development.&lt;/p&gt;




&lt;h2&gt;
  
  
  AI Agent Chat for Development Support
&lt;/h2&gt;

&lt;p&gt;We also integrated an &lt;strong&gt;AI agent chat&lt;/strong&gt; directly into the workspace.&lt;/p&gt;

&lt;p&gt;This allowed developers to:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;ask coding questions,&lt;/li&gt;
&lt;li&gt;debug issues faster,&lt;/li&gt;
&lt;li&gt;get explanations,&lt;/li&gt;
&lt;li&gt;and receive suggestions while building.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Rather than leaving the environment to search for answers, teams could interact with an AI assistant in real time while coding.&lt;/p&gt;

&lt;p&gt;This was especially useful during the buildathon, where every minute mattered and blocking issues needed immediate resolution.&lt;/p&gt;




&lt;h2&gt;
  
  
  Mentor Mode for Guided Collaboration
&lt;/h2&gt;

&lt;p&gt;Another important feature was &lt;strong&gt;mentor integration&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Mentors could join the workspace directly, observe what teams were building, and provide guidance in real time.&lt;/p&gt;

&lt;p&gt;This made mentorship more interactive:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;debugging could happen live,&lt;/li&gt;
&lt;li&gt;architectural suggestions could be given immediately,&lt;/li&gt;
&lt;li&gt;and teams could get feedback without breaking their flow.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Instead of mentorship happening in scheduled check-ins, it became part of the development process itself.&lt;/p&gt;




&lt;h2&gt;
  
  
  Tools, Support, and Buildathon Environment
&lt;/h2&gt;

&lt;p&gt;During the event, we also got exposure to observability and debugging tools like Sentry, along with credits that helped teams experiment quickly.&lt;/p&gt;

&lt;p&gt;The environment encouraged rapid prototyping,not polished production systems, but functional ideas built under pressure.&lt;/p&gt;

&lt;p&gt;That setup aligned perfectly with the challenge: build something useful in a very short time window.&lt;/p&gt;




&lt;h2&gt;
  
  
  Outcome and Ranking
&lt;/h2&gt;

&lt;p&gt;By the end of the buildathon, our project ranked &lt;strong&gt;3rd overall&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;But more importantly, we managed to turn a constraint into a product idea and build a working prototype within the limited time.&lt;/p&gt;




&lt;p&gt;The one-hour constraint was not just part of the challenge it shaped the direction of the idea itself.&lt;/p&gt;

&lt;p&gt;It highlighted how much of development time is often lost not in writing code, but in coordinating work between people.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Cursor for Communities&lt;/strong&gt; emerged from that realization: that collaboration tools matter just as much as coding tools, especially when time is limited.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>community</category>
      <category>productivity</category>
      <category>softwaredevelopment</category>
    </item>
    <item>
      <title>Not Everyone Has a GPU: My Gemma Hackathon Experience</title>
      <dc:creator>Valery Odinga</dc:creator>
      <pubDate>Thu, 21 May 2026 05:21:38 +0000</pubDate>
      <link>https://dev.to/odingaval/not-everyone-has-a-gpu-my-gemma-hackathon-experience-2lo7</link>
      <guid>https://dev.to/odingaval/not-everyone-has-a-gpu-my-gemma-hackathon-experience-2lo7</guid>
      <description>&lt;p&gt;When I joined the Gemma 4 challenge on DEV Community, I was genuinely excited. I had been looking forward to experimenting with modern open AI models in a real project environment and pushing myself technically during the hackathon.&lt;/p&gt;

&lt;p&gt;Like most developers entering hackathons, I started with big ideas.&lt;/p&gt;

&lt;p&gt;I wanted to build something meaningful, something that would really showcase what Gemma could do. On paper, everything looked possible. But once I started working locally, reality kicked in very quickly.&lt;/p&gt;

&lt;p&gt;My hardware simply could not keep up with the setup I originally wanted.&lt;/p&gt;

&lt;p&gt;At first, I tried forcing things to work. I closed every unnecessary application, monitored memory usage constantly, and spent hours messing with configurations just to make things run. Some attempts were painfully slow, others failed completely, and at certain moments my machine sounded like it was doing more than it should have.&lt;/p&gt;

&lt;p&gt;That was the moment I had to make a decision.&lt;/p&gt;

&lt;p&gt;I could either spend the entire hackathon fighting hardware limitations, or I could adapt and continue building with what I actually had.&lt;/p&gt;

&lt;p&gt;So I pivoted.&lt;/p&gt;

&lt;p&gt;Instead of using the larger setup I had originally planned for, I switched to &lt;strong&gt;Gemma 2B&lt;/strong&gt;. At that point, I focused on building my hackathon project: &lt;code&gt;AfyaKuu.&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;code&gt;AfyaKuu&lt;/code&gt; is an offline-first, privacy-preserving AI diagnostic and training platform designed for healthcare workers in low-resource, disconnected environments.&lt;/p&gt;

&lt;p&gt;Powered by Google &lt;strong&gt;Gemma 2&lt;/strong&gt;, &lt;code&gt;AfyaKuu&lt;/code&gt; provides real-time clinical support and interactive nurse education without requiring a single byte of internet connectivity.&lt;/p&gt;

&lt;p&gt;The idea behind the project was simple but important: bring accessible AI assistance to healthcare workers who often operate in environments where internet access is unreliable or completely unavailable. The system was designed to support decision-making and learning while respecting strict privacy constraints.&lt;/p&gt;

&lt;p&gt;Even with the smaller &lt;strong&gt;Gemma 2B&lt;/strong&gt; model, I was able to implement the core functionality and test real interactions. It wasn’t the perfect setup I had imagined at the beginning, but it worked — and that mattered more during a hackathon.&lt;/p&gt;

&lt;p&gt;And surprisingly, that constraint changed how I approached building.&lt;/p&gt;

&lt;p&gt;Working with limited resources forced me to think more carefully about efficiency, prompt design, and system behavior. I couldn’t rely on brute compute power, so I had to be intentional about every part of the pipeline. In a strange way, the limitation made the system design cleaner and more focused.&lt;/p&gt;

&lt;p&gt;It also made me reflect more deeply on accessibility in AI development.&lt;/p&gt;

&lt;p&gt;A lot of AI conversations assume access to powerful &lt;strong&gt;GPUs&lt;/strong&gt;, fast cloud infrastructure, and stable internet. But that is not the reality for many developers and users around the world. Students, indie builders, and engineers in low-resource environments are often left out of that narrative.&lt;/p&gt;

&lt;p&gt;For projects like &lt;code&gt;AfyaKuu&lt;/code&gt;, that gap is not theoretical — it is the entire problem being solved.&lt;/p&gt;

&lt;p&gt;Lightweight models like &lt;strong&gt;Gemma 2B&lt;/strong&gt; make it possible to actually deploy AI systems in places where infrastructure is limited. That changes who gets to build, and who gets to benefit.&lt;/p&gt;

&lt;p&gt;By the end of the hackathon, I realized the project was no longer just about using Gemma. It became a reminder that innovation does not always happen in ideal conditions. Sometimes it happens through constraints, adaptation, and persistence.&lt;/p&gt;

&lt;p&gt;Did I use the setup I originally imagined? No.&lt;/p&gt;

&lt;p&gt;Did I still build something meaningful? Yes.&lt;/p&gt;

&lt;p&gt;Not everyone has GPUs, cloud credits, or high-end machines.&lt;/p&gt;

&lt;p&gt;But people will still build anyway.&lt;/p&gt;

</description>
      <category>devchallenge</category>
      <category>gemmachallenge</category>
      <category>gemma</category>
    </item>
    <item>
      <title>TurboQuant: The Google Algorithm That Could Quietly Change the Future of AI</title>
      <dc:creator>Valery Odinga</dc:creator>
      <pubDate>Tue, 12 May 2026 09:57:17 +0000</pubDate>
      <link>https://dev.to/odingaval/turboquant-the-google-algorithm-that-could-quietly-change-the-future-of-ai-2n0g</link>
      <guid>https://dev.to/odingaval/turboquant-the-google-algorithm-that-could-quietly-change-the-future-of-ai-2n0g</guid>
      <description>&lt;p&gt;On March 24, 2026, researchers at Google introduced something that, at first glance, sounded almost forgettable:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TurboQuant.&lt;/strong&gt;&lt;br&gt;
Its just an algorithm.&lt;/p&gt;

&lt;p&gt;But hidden inside that algorithm is a solution to one of artificial intelligence’s biggest and most expensive problems: &lt;strong&gt;memory&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;And surprisingly, memory, may be the real bottleneck slowing AI down.&lt;/p&gt;




&lt;h2&gt;
  
  
  The Problem Nobody Talks About
&lt;/h2&gt;

&lt;p&gt;Modern AI systems like chatbots and virtual assistants appear almost magical. They remember context, answer questions instantly, summarize documents, and hold conversations that feel natural.&lt;/p&gt;

&lt;p&gt;But behind the scenes, these systems are struggling with a growing issue.&lt;/p&gt;

&lt;p&gt;Every conversation, every prompt, and every generated response creates more data that the model must keep track of. To do this, large language models use something called a &lt;strong&gt;key-value cache&lt;/strong&gt;, often shortened to a KV cache. This is like AI’s short-term memory.&lt;/p&gt;

&lt;p&gt;The longer the conversation becomes, the larger this memory grows. Eventually, memory usage becomes enormous, so much that AI companies spend billions on hardware simply to keep models running efficiently.&lt;/p&gt;

&lt;p&gt;In many cases, memory has become a greater limitation than processing power itself.&lt;/p&gt;

&lt;p&gt;That is where &lt;strong&gt;TurboQuant&lt;/strong&gt; enters the picture.&lt;/p&gt;




&lt;h2&gt;
  
  
  What Exactly Is TurboQuant?
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;TurboQuant&lt;/strong&gt; is a compression algorithm designed to reduce the amount of memory AI systems need while maintaining performance and accuracy.&lt;/p&gt;

&lt;p&gt;In simple terms, it allows AI to remember more while using far less space.&lt;/p&gt;

&lt;p&gt;Normally, compression comes with a tradeoff.&lt;/p&gt;

&lt;p&gt;Compress a photo too much and it becomes blurry. Compress audio too aggressively and it sounds distorted. The same is usually true for AI data: smaller memory often means lower accuracy.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;TurboQuant&lt;/strong&gt; attempts to break that tradeoff.&lt;/p&gt;

&lt;p&gt;According to Google Research, the algorithm can compress AI memory dramatically, in some cases down to only a 3 bits per stored value, while preserving the quality of the model’s responses.&lt;/p&gt;

&lt;p&gt;That is what makes it important.&lt;/p&gt;




&lt;h2&gt;
  
  
  The Two-Pipeline Strategy
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;TurboQuant&lt;/strong&gt; does not rely on a single trick. Instead, it works through two connected pipelines.&lt;/p&gt;

&lt;p&gt;The first pipeline is called &lt;strong&gt;PolarQuant&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Rather than compressing information directly, &lt;strong&gt;PolarQuant&lt;/strong&gt; reorganizes it into a more efficient form. It separates vectors into components such as direction and magnitude, making the data easier to shrink without losing essential meaning.&lt;/p&gt;

&lt;p&gt;Imagine giving out directions.&lt;/p&gt;

&lt;p&gt;Instead of saying:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;“Walk three steps east and four steps north,”&lt;br&gt;
you simply say:&lt;br&gt;
“Walk five steps in this direction.”&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;The information becomes cleaner and more compact.&lt;/p&gt;

&lt;p&gt;The second pipeline uses a mathematical concept called the &lt;strong&gt;Johnson–Lindenstrauss lemma&lt;/strong&gt; through a method known as &lt;strong&gt;Quantized Johnson–Lindenstrauss&lt;/strong&gt;, or &lt;strong&gt;QJL&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;This stage aggressively compresses the data while preserving relationships between pieces of information.&lt;/p&gt;

&lt;p&gt;That detail matters more than it sounds.&lt;/p&gt;

&lt;p&gt;AI models do not necessarily need exact numbers. What they need is the ability to preserve relationships — which words relate to each other, which ideas are similar, and which concepts are connected.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;QJL&lt;/strong&gt; helps maintain those relationships even after heavy compression.&lt;/p&gt;

&lt;p&gt;Together, the two pipelines allow &lt;strong&gt;TurboQuant&lt;/strong&gt; to shrink memory usage dramatically without severely damaging performance.&lt;/p&gt;




&lt;h2&gt;
  
  
  Why This Matters More Than People Realize
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;TurboQuant&lt;/strong&gt; may not attract the same attention as new AI &lt;strong&gt;chatbots&lt;/strong&gt; or image generators, but its implications are enormous.&lt;/p&gt;

&lt;p&gt;Lower memory usage means:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;cheaper AI infrastructure,&lt;/li&gt;
&lt;li&gt;faster inference speeds,&lt;/li&gt;
&lt;li&gt;longer context windows, and the possibility of running advanced models on smaller hardware.
That last point is especially important.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Today, the most powerful AI systems depend on expensive &lt;strong&gt;GPUs&lt;/strong&gt; and massive data centers. If algorithms like &lt;strong&gt;TurboQuant&lt;/strong&gt; reduce memory requirements enough, advanced AI could become more accessible to startups, researchers, schools, and developers around the world.&lt;/p&gt;

&lt;p&gt;It could also shift the economics of the AI industry itself.&lt;/p&gt;

&lt;p&gt;For years, the dominant assumption has been simple: better AI requires bigger hardware. **TurboQuant **challenges that idea by suggesting that smarter compression may matter just as much as raw computing power.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Quiet Revolution
&lt;/h2&gt;

&lt;p&gt;The most transformative technologies are not always the loudest.&lt;/p&gt;

&lt;p&gt;Sometimes progress comes from hidden optimizations deep inside infrastructure, improvements users may never see directly, but experience every day.&lt;/p&gt;

&lt;p&gt;If &lt;strong&gt;TurboQuant&lt;/strong&gt; succeeds, AI could become:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;faster,&lt;/li&gt;
&lt;li&gt;cheaper,&lt;/li&gt;
&lt;li&gt;and accessible on smaller devices.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;I experienced this limitation firsthand while working on a project that required &lt;strong&gt;Gemma 4&lt;/strong&gt;. My system simply did not have enough RAM to run it without crashing, forcing me to switch to the much smaller &lt;strong&gt;Gemma 2B&lt;/strong&gt; model instead.&lt;/p&gt;

&lt;p&gt;That experience revealed that:&lt;br&gt;
the future of AI is not only about building bigger models, but making powerful models efficient enough for everyone to use.&lt;/p&gt;

&lt;p&gt;And that is why &lt;strong&gt;TurboQuant&lt;/strong&gt; matters.&lt;/p&gt;

</description>
    </item>
    <item>
      <title>Stop Searching, Start Contributing: How GoodFirstGo is Making Open Source Approachable</title>
      <dc:creator>Valery Odinga</dc:creator>
      <pubDate>Tue, 31 Mar 2026 20:22:21 +0000</pubDate>
      <link>https://dev.to/odingaval/stop-searching-start-contributing-how-goodfirstgo-is-making-open-source-approachable-66g</link>
      <guid>https://dev.to/odingaval/stop-searching-start-contributing-how-goodfirstgo-is-making-open-source-approachable-66g</guid>
      <description>&lt;p&gt;Remember the first time you tried contributing to open source?&lt;/p&gt;

&lt;p&gt;If you were like most developers, the experience involved staring at a massive, complex codebase on GitHub, clicking the &lt;code&gt;Issues&lt;/code&gt; tab, and immediately feeling overwhelmed. The ecosystem is massive, and while hundreds of maintainers out there are actively asking for help, finding those rare "beginner-friendly" issues requires sifting through mountains of bugs and features that require deep domain knowledge.&lt;/p&gt;

&lt;p&gt;I realized developers shouldn't have to write custom GitHub API queries or dig through unrelated repositories just to make their first Pull Request.&lt;/p&gt;

&lt;p&gt;That’s exactly why I built &lt;code&gt;GoodFirstGo&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;What is &lt;code&gt;GoodFirstGo&lt;/code&gt;?&lt;br&gt;
&lt;code&gt;GoodFirstGo&lt;/code&gt; is a CLI tool built entirely in Go that brings the perfect open-source issues directly to your terminal.&lt;/p&gt;

&lt;p&gt;Instead of mindlessly browsing GitHub, you tell the CLI what language you want to work in, and it hands you a curated list of active repositories searching for help with the good-first-issue label.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Key Features Under the Hood&lt;/strong&gt;&lt;br&gt;
1.Smart Language Filtering: Want to practice your Python? Rust? Go? Just pass a &lt;code&gt;--language&lt;/code&gt; flag.&lt;br&gt;
2.Repository Health Filters: Filter out dead projects by mandating a minimum number of stars (&lt;code&gt;--stars 100&lt;/code&gt;).&lt;br&gt;
3.Recency: Nobody wants to comment on an issue from 2008. The &lt;code&gt;--age&lt;/code&gt; flag ensures you're only looking at issues created recently, this week, or this month.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Mode: This is my favorite part. By passing the &lt;code&gt;--learning&lt;/code&gt; flag, the CLI will output specialized tutorials and resources tailored to the specific language of the issue you are about to tackle!&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;Seeing it in Action&lt;/strong&gt;&lt;br&gt;
Because GoodFirstGo compiles down to a single binary, you don't need any complex runtimes or dependencies to use it. If you have Go installed on your machine, getting started takes ten seconds:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;bash
go &lt;span class="nb"&gt;install &lt;/span&gt;github.com/odingaval/GoodFirstGo/cmd/goodfirstgo@latest
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Once installed globally, you can query GitHub instantly. Let's say I want to find a beginner-friendly Go issue in a repository that has at least 500 stars, and I want to see learning resources for Go before I dive in.&lt;/p&gt;

&lt;p&gt;I just type:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;bash
goodfirstgo &lt;span class="nt"&gt;--language&lt;/span&gt; go &lt;span class="nt"&gt;--stars&lt;/span&gt; 500 &lt;span class="nt"&gt;--learning&lt;/span&gt; &lt;span class="nt"&gt;--limit&lt;/span&gt; 5
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Instantly, I get a clean UI output of 5 high-quality repositories looking for help, right in my terminal window. Add a Github Token to your environment, and it bypasses rate limits entirely.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Why build a CLI instead of a website?&lt;/strong&gt;&lt;br&gt;
Modern web apps are great, but the Terminal is where developers live. By keeping the tool inside the CLI environment, you can search for issues, clone the resulting repository, and open your IDE without your hands ever leaving the keyboard.&lt;/p&gt;

&lt;p&gt;Plus, writing a CLI in Go is just incredibly fun. It leverages Go's standard &lt;code&gt;net/http&lt;/code&gt; efficiently alongside Cobra for powerful, responsive shell commands.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Looking to Contribute?&lt;/strong&gt;&lt;br&gt;
The absolute best part about &lt;code&gt;GoodFirstGo&lt;/code&gt;? Because it is a tool explicitly designed to get beginners into open-source software, the project itself is heavily monitored for first-time contributors!&lt;/p&gt;

&lt;p&gt;If you've never made an open-source contribution before, cloning the repository and adding a small feature to &lt;code&gt;GoodFirstGo&lt;/code&gt; is the perfect place to start.&lt;/p&gt;

&lt;p&gt;Check out the source code, download the latest binary, or star the repository here: 👉 &lt;code&gt;github.com/odingaval/GoodFirstGo&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Let me know what your first Pull Request ends up being!&lt;/p&gt;

</description>
      <category>beginners</category>
      <category>go</category>
      <category>opensource</category>
      <category>showdev</category>
    </item>
    <item>
      <title>Building a Concurrent TCP Chat Server in Go (NetCat Clone)</title>
      <dc:creator>Valery Odinga</dc:creator>
      <pubDate>Tue, 24 Mar 2026 13:05:53 +0000</pubDate>
      <link>https://dev.to/odingaval/building-a-concurrent-tcp-chat-server-in-go-netcat-clone-jc1</link>
      <guid>https://dev.to/odingaval/building-a-concurrent-tcp-chat-server-in-go-netcat-clone-jc1</guid>
      <description>&lt;p&gt;In this project, we built a simplified version of the classic NetCat ("nc") tool — a TCP-based chat server that allows multiple clients to connect, send messages, and interact in real time.&lt;/p&gt;

&lt;p&gt;The goal was not just to recreate a chat system, but to deeply understand:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;TCP networking&lt;/li&gt;
&lt;li&gt;Go concurrency (goroutines &amp;amp; channels)&lt;/li&gt;
&lt;li&gt;State management in concurrent systems&lt;/li&gt;
&lt;li&gt;Client-server architecture&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;At its core, the system needed to:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Accept multiple client connections&lt;/li&gt;
&lt;li&gt;Allow clients to send messages&lt;/li&gt;
&lt;li&gt;Broadcast messages to other clients&lt;/li&gt;
&lt;li&gt;Track when users join or leave&lt;/li&gt;
&lt;li&gt;Handle unexpected disconnects (like Ctrl+C)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;This introduces a key challenge:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;«Multiple clients interacting with shared state at the same time.»&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;TCP Server Basics&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;The server listens for incoming connections using:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;listener, _ := net.Listen("tcp", ":8989")&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Then continuously accepts clients:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;conn&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;_&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;listener&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Accept&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
    &lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="n"&gt;handleConnection&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;conn&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Important concept:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;"Accept()" blocks until a client connects&lt;/li&gt;
&lt;li&gt;Each client is handled in a separate goroutine&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This allows multiple users to connect simultaneously.&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Goroutines and Concurrency&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Each client runs in its own goroutine:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;go handleConnection(conn)&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;This means:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;One slow client does not block others&lt;/li&gt;
&lt;li&gt;Each connection is handled independently&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;However, this introduces a problem:&lt;/p&gt;

&lt;p&gt;«Multiple goroutines modifying shared data can cause race conditions.»&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;The Shared State Problem&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;We needed to track all connected clients:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;var connections map[net.Conn]string&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;But multiple goroutines might:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Add clients&lt;/li&gt;
&lt;li&gt;Remove clients&lt;/li&gt;
&lt;li&gt;Broadcast messages&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;At the same time.&lt;/p&gt;

&lt;p&gt;This can cause:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Data corruption&lt;/li&gt;
&lt;li&gt;Crashes ("fatal error: concurrent map writes")&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;Solution 1: Mutex&lt;/p&gt;

&lt;p&gt;One approach is using a mutex:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;mu&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Lock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;connections&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;conn&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;name&lt;/span&gt;
&lt;span class="n"&gt;mu&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Unlock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;But this introduces:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Complexity&lt;/li&gt;
&lt;li&gt;Potential deadlocks&lt;/li&gt;
&lt;li&gt;Performance bottlenecks&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;Solution 2: Channels (The Go Way)&lt;/p&gt;

&lt;p&gt;Instead of sharing memory, we used channels to communicate changes.&lt;/p&gt;

&lt;p&gt;This follows Go’s philosophy:&lt;/p&gt;

&lt;p&gt;«“Do not communicate by sharing memory; share memory by communicating.”»&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;ChatRoom Architecture&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;We designed a "ChatRoom" struct:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;
&lt;span class="k"&gt;type&lt;/span&gt; &lt;span class="n"&gt;ChatRoom&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;chatters&lt;/span&gt; &lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;Client&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt;
    &lt;span class="n"&gt;history&lt;/span&gt;  &lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;

    &lt;span class="n"&gt;Register&lt;/span&gt;   &lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;Client&lt;/span&gt;
    &lt;span class="n"&gt;Unregister&lt;/span&gt; &lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;Client&lt;/span&gt;
    &lt;span class="n"&gt;Broadcast&lt;/span&gt;  &lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="n"&gt;Message&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

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

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Only one goroutine manages "chatters" and "history"&lt;/li&gt;
&lt;li&gt;Other goroutines send events via channels&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;&lt;strong&gt;The Event Loop&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;The core of the system is the "Run()" method:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;
&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;select&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;client&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;Register&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
    &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;client&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;Unregister&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
    &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;msg&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;Broadcast&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This acts like a central controller.&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Handling Events&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;1. Client Join&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Ask for name&lt;/li&gt;
&lt;li&gt;Add to chatters map&lt;/li&gt;
&lt;li&gt;Send chat history&lt;/li&gt;
&lt;li&gt;Broadcast join message&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;code&gt;cr.chatters[client] = struct{}{}&lt;/code&gt;&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;2. Message Broadcast&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Append to history&lt;/li&gt;
&lt;li&gt;Send to all clients except sender
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="k"&gt;range&lt;/span&gt; &lt;span class="n"&gt;cr&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;chatters&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="n"&gt;sender&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;receive&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;message&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;p&gt;&lt;strong&gt;3. Client Leave&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Remove from map&lt;/li&gt;
&lt;li&gt;Close channel&lt;/li&gt;
&lt;li&gt;Broadcast leave message&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;Handling Ctrl+C (Unexpected Disconnects)&lt;/p&gt;

&lt;p&gt;When a client presses Ctrl+C:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;TCP connection closes&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;"ReadString()&lt;/code&gt;" returns "io.EOF"&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;We detect this:&lt;br&gt;
&lt;code&gt;&lt;br&gt;
if err != nil {&lt;br&gt;
    // client disconnected&lt;br&gt;
}&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;And broadcast:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;"%s has left the chat"&lt;/code&gt;&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Message Flow&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Here’s how a message travels:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Client sends message&lt;/li&gt;
&lt;li&gt;Goroutine reads it&lt;/li&gt;
&lt;li&gt;Sends it to "Broadcast" channel&lt;/li&gt;
&lt;li&gt;"Run()" receives it&lt;/li&gt;
&lt;li&gt;Loops through clients&lt;/li&gt;
&lt;li&gt;Sends message to each client’s "receive" channel&lt;/li&gt;
&lt;li&gt;Client writer goroutine prints it&lt;/li&gt;
&lt;/ol&gt;




&lt;p&gt;Main Concepts were:&lt;/p&gt;

&lt;p&gt;&lt;em&gt;1. TCP is Just a Stream&lt;/em&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Everything is bytes&lt;/li&gt;
&lt;li&gt;Messages are manually structured ("\n")&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;_&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Blocking is Normal_&lt;/li&gt;
&lt;/ol&gt;

&lt;ul&gt;
&lt;li&gt;"Accept()" blocks waiting for connections&lt;/li&gt;
&lt;li&gt;"ReadString()" blocks waiting for input&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;But only within their goroutine.&lt;/p&gt;




&lt;p&gt;&lt;em&gt;3. Goroutines Enable Concurrency&lt;/em&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Lightweight threads managed by Go&lt;/li&gt;
&lt;li&gt;Thousands can run efficiently&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;&lt;em&gt;4. Channels Simplify Concurrency&lt;/em&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Avoid shared memory issues&lt;/li&gt;
&lt;li&gt;Centralize state management&lt;/li&gt;
&lt;li&gt;Create predictable flow&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;Challenges Faced&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Handling empty messages&lt;/li&gt;
&lt;li&gt;Debugging raw string issues&lt;/li&gt;
&lt;li&gt;Understanding blocking behavior&lt;/li&gt;
&lt;li&gt;Managing client disconnects&lt;/li&gt;
&lt;li&gt;Avoiding race conditions&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;This project goes beyond just building a chat app.&lt;/p&gt;

&lt;p&gt;It revealed:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;How real-time systems work&lt;/li&gt;
&lt;li&gt;How servers handle multiple users&lt;/li&gt;
&lt;li&gt;How to design safe concurrent programs&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In many ways, this is a mini version of real-world systems like chat apps, multiplayer servers, and messaging platforms.&lt;/p&gt;




&lt;p&gt;Building this TCP chat server helped me understand how powerful Go is for concurrent systems.&lt;/p&gt;

&lt;p&gt;By combining:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;TCP networking&lt;/li&gt;
&lt;li&gt;Goroutines&lt;/li&gt;
&lt;li&gt;Channels&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;we can build scalable, real-time applications with relatively simple code.&lt;/p&gt;




</description>
      <category>backend</category>
      <category>go</category>
      <category>networking</category>
      <category>tutorial</category>
    </item>
    <item>
      <title>What Actually Happens When a Form Hits a Go Server</title>
      <dc:creator>Valery Odinga</dc:creator>
      <pubDate>Wed, 04 Feb 2026 08:31:26 +0000</pubDate>
      <link>https://dev.to/odingaval/what-actually-happens-when-a-form-hits-a-go-server-2ohm</link>
      <guid>https://dev.to/odingaval/what-actually-happens-when-a-form-hits-a-go-server-2ohm</guid>
      <description>&lt;p&gt;I’ve been learning how to build web servers in Go, and just yesterday, I tried connecting a simple HTML form to my backend.&lt;/p&gt;

&lt;p&gt;I expected the flow to be straightforward: user clicks Submit, Go runs my code, output appears. Instead, the page refreshed, my server logs looked fine, but nothing rendered.&lt;/p&gt;

&lt;p&gt;That experience made me realize I didn’t fully understand what actually happens when a form hits a Go server. &lt;br&gt;
This article breaks down that process from the browser sending a request, to Go’s &lt;code&gt;net/http&lt;/code&gt;handlers responding focusing on the clear understanding that finally made things click for me.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;What Happens When You Click “Submit”&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Clicking Submit doesn’t run your Go code. It sends an HTTP request.&lt;/p&gt;

&lt;p&gt;The browser packages the form data, chooses a method (usually POST), and sends everything to the server. After that, the browser just waits.&lt;/p&gt;

&lt;p&gt;On the Go side, the server is already running and listening. When the request arrives, &lt;code&gt;net/http&lt;/code&gt;matches the URL to a handler function and calls it. That’s the moment your code actually runs.&lt;/p&gt;

&lt;p&gt;Inside the handler, you read the form values, process them, and write a response using &lt;code&gt;http.ResponseWriter.&lt;/code&gt; Whatever you write there is what the browser receives and displays.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Why My POST Route Wasn’t Responding&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;At one point, my server was running fine. The homepage loaded, and my logs showed that the POST route was being hit. Still, nothing showed up in the browser.&lt;/p&gt;

&lt;p&gt;The issue wasn’t that the handler wasn’t running it was that I wasn’t sending anything back.&lt;/p&gt;

&lt;p&gt;In Go, handling a request and responding to it are two separate steps. If your handler reads the form data but never writes to&lt;code&gt;http.ResponseWriter&lt;/code&gt;, the browser has nothing to display.&lt;/p&gt;

&lt;p&gt;Also the GET and POST aren’t interchangeable. A form that sends a POST request will never hit a GET-only handler, even if the URL looks correct. If the method doesn’t match, your code simply won’t run.&lt;/p&gt;

&lt;p&gt;Once I made sure the request method matched and that I was actually writing a response, things finally started to work.&lt;/p&gt;

&lt;p&gt;In Go,&lt;code&gt;http.ResponseWriter&lt;/code&gt; is how your handler talks back to the browser. Think of it as a pen: whatever you write with it becomes the body of the HTTP response.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;em&gt;For example:&lt;/em&gt;&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;func handler(w http.ResponseWriter, r *http.Request) {
    fmt.Fprintln(w, "Hello, world!")
}
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;w&lt;/code&gt; is the &lt;code&gt;ResponseWriter&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;Fprintln(w, ...)&lt;/code&gt; writes text into the response.&lt;/p&gt;

&lt;p&gt;When the handler finishes, the server sends everything you wrote back to the browser.&lt;/p&gt;

&lt;p&gt;If you never write to&lt;code&gt;w&lt;/code&gt;, the request still “works” on the server side, but the user sees… nothing. That’s exactly why my POST requests seemed to do nothing: the handler ran, but didn’t write a response.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;ResponseWriter&lt;/code&gt; also lets you set headers, status codes, or even send files. But at its core, it’s just the channel for your server’s response.&lt;/p&gt;

&lt;p&gt;Running a Go server isn’t magic it just listens for requests. Clicking a form’s Submit button sends an HTTP request. Your handler runs when the request matches its URL and method, and &lt;code&gt;http.ResponseWriter&lt;/code&gt; is how you send the output back to the browser.&lt;/p&gt;

&lt;p&gt;Once I understood this simple flow, everything clicked: method mismatches explain why GET worked but POST didn’t, and writing to &lt;code&gt;ResponseWriter&lt;/code&gt; explains why nothing showed up at first.&lt;/p&gt;

&lt;p&gt;If you’re starting with Go web servers, remember: request arrives → handler runs → write a response. Master that, and the rest becomes much easier.&lt;/p&gt;

</description>
      <category>backend</category>
      <category>beginners</category>
      <category>go</category>
      <category>webdev</category>
    </item>
    <item>
      <title>Creating an AI App with Genkit and Gemini: A Beginner’s Guide</title>
      <dc:creator>Valery Odinga</dc:creator>
      <pubDate>Wed, 08 Oct 2025 14:36:25 +0000</pubDate>
      <link>https://dev.to/odingaval/creating-an-ai-app-with-genkit-and-gemini-a-beginners-guide-48md</link>
      <guid>https://dev.to/odingaval/creating-an-ai-app-with-genkit-and-gemini-a-beginners-guide-48md</guid>
      <description>&lt;p&gt;Artificial Intelligence (AI) tools are now easier than ever to build and Genkit by Google makes it surprisingly simple to create, test, and run your own AI-powered applications.&lt;/p&gt;

&lt;p&gt;In this guide, I’ll walk you through how I created a Recipe Generator App using Genkit and Gemini, set up the environment, and explored its interactive Developer UI.&lt;/p&gt;

&lt;p&gt;But wait, what is Genkit Really?&lt;/p&gt;

&lt;p&gt;Genkit is an open-source framework by Google that helps developers build AI agents and workflows quickly and intuitively.&lt;/p&gt;

&lt;p&gt;It integrates seamlessly with Gemini, Vertex AI, and other AI providers, allowing you to focus on your app’s logic instead of boilerplate code or API setup.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 1: Setting Up the Environment&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Make sure you have the following installed:&lt;/p&gt;

&lt;p&gt;Node.js (v18 or later)&lt;/p&gt;

&lt;p&gt;npm or yarn&lt;/p&gt;

&lt;p&gt;A Gemini API key (you can get one from Google AI Studio&lt;br&gt;
Then create a new folder for your project and install Genkit:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;npm install genkit @genkit-ai/google-genai&lt;br&gt;
&lt;/code&gt;&lt;br&gt;
That’s it! You now have everything you need to start building.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 2: Set Your Gemini API Key&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Genkit needs your Gemini API key to connect with the model.&lt;/p&gt;

&lt;p&gt;You can set it temporarily in your current terminal session:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;export GEMINI_API_KEY=&amp;lt;your-api-key&amp;gt;&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Or, make it permanent by adding it to your shell profile:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;echo 'export GEMINI_API_KEY=&amp;lt;your-api-key&amp;gt;' &amp;gt;&amp;gt; ~/.bashrc
source ~/.bashrc
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;but I stored mine in a .env file and loaded it with dotenv for better security. That's also another option for you.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 3: Create Your First Genkit App&lt;/strong&gt; (Recipe Generator)&lt;br&gt;
Let’s create something fun, a recipe generator that crafts meal ideas based on ingredients.&lt;/p&gt;

&lt;p&gt;Start by creating your project structure:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;mkdir src
touch src/index.ts
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then add the following code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import 'dotenv/config';
import { googleAI } from '@genkit-ai/google-genai';
import { genkit, z } from 'genkit';

// Initialize Genkit with the Google AI plugin
const ai = genkit({
  plugins: [googleAI()],
  model: googleAI.model('gemini-2.5-flash', {
    temperature: 0.8,
  }),
});

// Define input schema
const RecipeInputSchema = z.object({
  ingredient: z.string().describe('Main ingredient or cuisine type'),
  dietaryRestrictions: z.string().optional().describe('Any dietary restrictions'),
});

// Define output schema
const RecipeSchema = z.object({
  title: z.string(),
  description: z.string(),
  prepTime: z.string(),
  cookTime: z.string(),
  servings: z.number(),
  ingredients: z.array(z.string()),
  instructions: z.array(z.string()),
  tips: z.array(z.string()).optional(),
});

// Define a recipe generator flow
export const recipeGeneratorFlow = ai.defineFlow(
  {
    name: 'recipeGeneratorFlow',
    inputSchema: RecipeInputSchema,
    outputSchema: RecipeSchema,
  },
  async (input) =&amp;gt; {
    // Create a prompt based on the input
    const prompt = `Create a recipe with the following requirements:
      Main ingredient: ${input.ingredient}
      Dietary restrictions: ${input.dietaryRestrictions || 'none'}`;

    // Generate structured recipe data using the same schema
    const { output } = await ai.generate({
      prompt,
      output: { schema: RecipeSchema },
    });

    if (!output) throw new Error('Failed to generate recipe');

    return output;
  },
);

// Run the flow
async function main() {
  const recipe = await recipeGeneratorFlow({
    ingredient: 'avocado',
    dietaryRestrictions: 'vegetarian',
  });

  console.log(recipe);
}

main().catch(console.error);
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This defines a Genkit flow that sends a text prompt to Gemini and returns an AI-generated recipe.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 4: Run and Test the Flow&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Start your Genkit development server:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;genkit start -- npx tsx --watch src/index.ts&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;You’ll see output like this:&lt;/p&gt;

&lt;p&gt;&lt;code&gt;Genkit Developer UI running at http://localhost:4000&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Step 5: Interacting with the Developer UI&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Open your browser and navigate to &lt;a href="http://localhost:4000" rel="noopener noreferrer"&gt;http://localhost:4000&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This is the Genkit Developer UI, a powerful playground for testing and debugging your AI flows.&lt;/p&gt;

&lt;p&gt;Here’s what you can do inside the Developer UI:&lt;br&gt;
1.&lt;strong&gt;&lt;em&gt;Explore Your Flows&lt;/em&gt;&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;You’ll see your recipeGenerator flow listed under the Flows tab.&lt;br&gt;
Click it to open an interactive testing panel.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;&lt;em&gt;Provide Inputs&lt;/em&gt;&lt;/strong&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Enter your ingredients into the input box (for example,&lt;br&gt;
chicken, garlic, tomatoes, basil)&lt;br&gt;
and hit Run Flow.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;&lt;em&gt;View AI Responses&lt;/em&gt;&lt;/strong&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;You’ll get an instant response from Gemini — usually a full recipe suggestion!&lt;br&gt;
The UI also shows structured input/output data, so you can see exactly how your flow behaves.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;strong&gt;&lt;em&gt;Inspect Traces&lt;/em&gt;&lt;/strong&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Switch to the Traces tab to dive deeper into how your flow executed.&lt;br&gt;
You can monitor latency, errors, and data transformations — great for debugging or optimization.&lt;/p&gt;

&lt;p&gt;You just built your first Genkit app!&lt;/p&gt;

&lt;p&gt;From here, you can:&lt;br&gt;
Add more steps to your flow (like nutrition facts or cooking time)&lt;br&gt;
Integrate it with a web frontend or API endpoint&lt;br&gt;
Explore the Genkit dashboard for real-time monitoring and collaboration&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>tutorial</category>
      <category>ai</category>
      <category>beginners</category>
    </item>
    <item>
      <title>Blockchain Was Cool, But Superchains Are Cooler</title>
      <dc:creator>Valery Odinga</dc:creator>
      <pubDate>Thu, 17 Jul 2025 08:06:56 +0000</pubDate>
      <link>https://dev.to/odingaval/blockchain-was-cool-but-superchains-are-cooler-3caf</link>
      <guid>https://dev.to/odingaval/blockchain-was-cool-but-superchains-are-cooler-3caf</guid>
      <description>&lt;p&gt;Welcome to the World of Blockchain (No, It’s Not a Fancy Prison 🔗)&lt;/p&gt;

&lt;p&gt;If you’ve heard of Bitcoin or Ethereum, you’ve heard of blockchain—the tech behind them. But what is it? &lt;/p&gt;

&lt;p&gt;Imagine blockchain as a giant, un-cheatable spreadsheet that everyone can see but no one can secretly edit. Instead of living on one computer, it’s copied across thousands, making it nearly impossible to hack. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Why does this matter?&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;No more needing a bank to send money &lt;/p&gt;

&lt;p&gt;No sneaky changes—once something’s recorded, it’s there forever &lt;/p&gt;

&lt;p&gt;It’s like digital democracy for money &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;How Blockchain Works (Without Making Your Brain Hurt&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Let’s break it down with a pizza analogy  (because everything’s better with pizza).&lt;/p&gt;

&lt;p&gt;You order a pizza (this is your "transaction") &lt;/p&gt;

&lt;p&gt;The pizza shop writes it down in their ledger (a "block") &lt;/p&gt;

&lt;p&gt;They add it to a chain of all past orders (the "blockchain") ⛓️&lt;/p&gt;

&lt;p&gt;Every customer has a copy of this ledger—so if the shop tries to say you didn’t pay, everyone else has proof you did. &lt;/p&gt;

&lt;p&gt;*&lt;em&gt;Boom. That’s blockchain. *&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;*&lt;em&gt;The Problem: Blockchains Can Be Slow and Expensive *&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Early blockchains (Bitcoin and old-school Ethereum) are like a single cashier at a packed fast-food joint. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Slow?&lt;/strong&gt; Transactions take minutes (or hours) &lt;br&gt;
 &lt;strong&gt;Expensive?&lt;/strong&gt; Fees can cost more than your coffee &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Congested?&lt;/strong&gt; Too many orders = delays &lt;/p&gt;

&lt;p&gt;This is why we needed an upgrade. Enter…&lt;/p&gt;

&lt;p&gt;*&lt;em&gt;Superchains: The Blockchain Avengers *&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;If regular blockchains are &lt;strong&gt;flip phones&lt;/strong&gt; , Superchains are &lt;strong&gt;5G smartphones&lt;/strong&gt;—faster, smarter, and way more powerful.&lt;/p&gt;

&lt;p&gt;*&lt;em&gt;What Makes Superchains So Cool? *&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Modular Design – Like a buffet where each dish is made by a specialist  (one chain handles security, another speed, etc.).&lt;/p&gt;

&lt;p&gt;Shared Security – Instead of every chain hiring its own bouncer , they share a super-bouncer .&lt;/p&gt;

&lt;p&gt;Instant Communication – Different blockchains can talk seamlessly (like WhatsApp for crypto) &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Real-World Example: Optimism’s Superchain&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Optimism (a big Ethereum upgrade) is building a Superchain highway , where multiple blockchains run together—faster, cheaper, and way smoother.&lt;/p&gt;

&lt;p&gt;*&lt;em&gt;Why Should You Care? *&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Faster transactions – No more waiting 10 minutes for your coffee payment to go through.&lt;/p&gt;

&lt;p&gt;Lower fees  – Sending crypto could cost pennies instead of dollars.&lt;/p&gt;

&lt;p&gt;More apps, less hassle – Games, social media, and finance apps will work like the internet, but decentralized.&lt;/p&gt;

&lt;p&gt;*&lt;em&gt;Final Thought: The Future is Super *&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Blockchain was the Model T Ford revolutionary but clunky. Superchains? They’re the Tesla of crypto sleek, fast, and ready for mass adoption.&lt;/p&gt;

&lt;p&gt;So, if you thought blockchain was cool… just wait until you see what Superchains can do. &lt;/p&gt;

</description>
    </item>
  </channel>
</rss>
