<?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: Steven Nguyen</title>
    <description>The latest articles on DEV Community by Steven Nguyen (@steven_nguyen).</description>
    <link>https://dev.to/steven_nguyen</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%2F3554848%2Fa41bbeab-c346-4c8b-a6b3-8c89403a9d46.png</url>
      <title>DEV Community: Steven Nguyen</title>
      <link>https://dev.to/steven_nguyen</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/steven_nguyen"/>
    <language>en</language>
    <item>
      <title>🚀 Why Docker, Kubernetes, and Microservices Are the Foundation of Scalable Applications</title>
      <dc:creator>Steven Nguyen</dc:creator>
      <pubDate>Thu, 09 Oct 2025 03:30:11 +0000</pubDate>
      <link>https://dev.to/steven_nguyen/why-docker-kubernetes-and-microservices-are-the-foundation-of-scalable-applications-291p</link>
      <guid>https://dev.to/steven_nguyen/why-docker-kubernetes-and-microservices-are-the-foundation-of-scalable-applications-291p</guid>
      <description>&lt;p&gt;In today’s software world, scalability is no longer a “nice-to-have” — it’s a survival skill.&lt;br&gt;&lt;br&gt;
Applications must handle millions of requests, scale dynamically, and recover automatically from failures.&lt;/p&gt;

&lt;p&gt;But how do modern systems achieve that level of resilience and flexibility?&lt;br&gt;&lt;br&gt;
The answer lies in the &lt;strong&gt;trinity of modern architecture&lt;/strong&gt;:&lt;br&gt;&lt;br&gt;
&lt;strong&gt;Docker&lt;/strong&gt;, &lt;strong&gt;Kubernetes&lt;/strong&gt;, and &lt;strong&gt;Microservices&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;Together, they’ve completely changed how we build, deploy, and manage applications at scale.&lt;/p&gt;




&lt;h2&gt;
  
  
  💡 The Shift from Monoliths to Microservices
&lt;/h2&gt;

&lt;p&gt;Not long ago, most enterprise systems were &lt;strong&gt;monolithic&lt;/strong&gt; — one giant codebase that handled everything.&lt;br&gt;&lt;br&gt;
Scaling such applications meant adding more CPU and RAM to a single server — an expensive and fragile solution.&lt;/p&gt;

&lt;p&gt;Then came &lt;strong&gt;microservices&lt;/strong&gt; — a paradigm shift that broke monoliths into &lt;strong&gt;smaller, independent services&lt;/strong&gt;, each focusing on a single business capability.&lt;/p&gt;

&lt;p&gt;Instead of one big app, you now have dozens (or hundreds) of lightweight services that can:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Be deployed independently
&lt;/li&gt;
&lt;li&gt;Scale individually
&lt;/li&gt;
&lt;li&gt;Communicate through APIs or event streams
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This architectural shift made &lt;strong&gt;horizontal scaling&lt;/strong&gt; — also known as &lt;em&gt;scale-out&lt;/em&gt; — not just possible, but efficient.&lt;/p&gt;




&lt;h2&gt;
  
  
  🐳 Docker — The Foundation of Portability
&lt;/h2&gt;

&lt;p&gt;At the heart of microservices lies &lt;strong&gt;Docker&lt;/strong&gt;, the containerization platform that revolutionized deployment.&lt;/p&gt;

&lt;p&gt;Docker lets you package your application, its dependencies, and configuration into a single image that runs identically everywhere — on a developer’s laptop, a test server, or a cloud cluster.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Benefits of Docker for scalable apps:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;✅ Consistency — “It works on my machine” is no longer a problem
&lt;/li&gt;
&lt;li&gt;⚙️ Fast deployment — Start or stop containers in seconds
&lt;/li&gt;
&lt;li&gt;📦 Isolation — Each service runs independently, preventing dependency conflicts
&lt;/li&gt;
&lt;li&gt;🧩 Reusability — Build once, deploy anywhere
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In microservices, each service runs inside its own Docker container — lightweight, isolated, and easy to manage.&lt;/p&gt;




&lt;h2&gt;
  
  
  ☸️ Kubernetes — The Orchestrator of Scale
&lt;/h2&gt;

&lt;p&gt;While Docker handles packaging and running containers, &lt;strong&gt;Kubernetes (K8s)&lt;/strong&gt; takes care of &lt;strong&gt;orchestrating&lt;/strong&gt; them across clusters.&lt;/p&gt;

&lt;p&gt;Think of Kubernetes as the &lt;strong&gt;conductor of your container orchestra&lt;/strong&gt;.&lt;br&gt;&lt;br&gt;
It manages where containers run, how many replicas to keep alive, and how to recover from failures automatically.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Key features that make Kubernetes essential for scale-out applications:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;⚡ Auto-scaling: Add or remove containers based on real-time demand
&lt;/li&gt;
&lt;li&gt;🔁 Self-healing: Automatically restarts failed pods and reschedules them on healthy nodes
&lt;/li&gt;
&lt;li&gt;🌐 Load balancing &amp;amp; service discovery: Keeps traffic flowing evenly to healthy services
&lt;/li&gt;
&lt;li&gt;🚀 Rolling updates: Deploy new versions without downtime
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;With Kubernetes, scaling an application isn’t about buying a bigger server — it’s about letting the system automatically grow or shrink based on load.&lt;/p&gt;




&lt;h2&gt;
  
  
  🧩 Microservices — The Architecture of Flexibility
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Microservices&lt;/strong&gt; define the way your system is built — small, decoupled services communicating via APIs, often REST or GraphQL, or event streams through Kafka.&lt;/p&gt;

&lt;p&gt;Each microservice can:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Have its own database (PostgreSQL, MongoDB, etc.)
&lt;/li&gt;
&lt;li&gt;Be written in any language (Java, Go, Node.js, etc.)
&lt;/li&gt;
&lt;li&gt;Deploy independently without affecting others
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This modular design gives development teams agility — they can release features faster, fix bugs in isolation, and adopt new technologies gradually.&lt;/p&gt;

&lt;p&gt;In short:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Docker packages the service.&lt;br&gt;&lt;br&gt;
Kubernetes runs and scales it.&lt;br&gt;&lt;br&gt;
Microservices define how it fits into the whole system.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  🏗️ How They Work Together
&lt;/h2&gt;

&lt;p&gt;Imagine you’re building an e-commerce platform.&lt;br&gt;&lt;br&gt;
You might have separate services for:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;🛒 Orders
&lt;/li&gt;
&lt;li&gt;👤 Users
&lt;/li&gt;
&lt;li&gt;💳 Payments
&lt;/li&gt;
&lt;li&gt;📦 Shipping
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Each service runs in its own &lt;strong&gt;Docker container&lt;/strong&gt;, is managed by &lt;strong&gt;Kubernetes&lt;/strong&gt;, and communicates with others via REST APIs or Kafka events.&lt;/p&gt;

&lt;p&gt;When Black Friday traffic spikes, Kubernetes automatically scales the &lt;strong&gt;Order&lt;/strong&gt; and &lt;strong&gt;Payment&lt;/strong&gt; services horizontally — spinning up more containers as needed.&lt;br&gt;&lt;br&gt;
When demand drops, it scales them down, saving resources.&lt;/p&gt;

&lt;p&gt;That’s &lt;strong&gt;scale-out architecture&lt;/strong&gt; in action — efficient, resilient, and cloud-native.&lt;/p&gt;




&lt;h2&gt;
  
  
  ⚙️ The Enterprise Impact
&lt;/h2&gt;

&lt;p&gt;Today, some of the world’s largest systems — Netflix, Amazon, Alibaba — run on microservices orchestrated by Kubernetes.&lt;br&gt;&lt;br&gt;
This approach lets enterprises:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Scale globally in real time
&lt;/li&gt;
&lt;li&gt;Reduce downtime and deployment risk
&lt;/li&gt;
&lt;li&gt;Improve developer productivity through CI/CD pipelines
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;It’s not just a trend; it’s the &lt;strong&gt;new foundation&lt;/strong&gt; of software infrastructure.&lt;/p&gt;




&lt;h2&gt;
  
  
  💬 Final Thoughts
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Docker, Kubernetes, and Microservices&lt;/strong&gt; have reshaped modern application architecture.&lt;/p&gt;

&lt;p&gt;They bring &lt;strong&gt;consistency, automation, and flexibility&lt;/strong&gt; to every stage of development — from local testing to global deployment.&lt;/p&gt;

&lt;p&gt;If you’re building applications that need to scale out, recover gracefully, and evolve quickly, this trio isn’t optional — it’s essential.&lt;/p&gt;

&lt;p&gt;The future of enterprise scalability is not about bigger machines — it’s about &lt;strong&gt;smarter, distributed systems&lt;/strong&gt; built on containers, orchestration, and modular design.&lt;/p&gt;




&lt;p&gt;👨‍💻 &lt;em&gt;Written by Steven Nguyen&lt;/em&gt;&lt;br&gt;&lt;br&gt;
Engineering Manager | Designing scalable cloud-native systems with Docker, Kubernetes, and Microservices.&lt;/p&gt;

</description>
      <category>microservices</category>
      <category>architecture</category>
      <category>kubernetes</category>
      <category>docker</category>
    </item>
    <item>
      <title>🏢 Why Spring Boot, Kafka, Oracle, and Tomcat Still Power the Enterprise in 2025</title>
      <dc:creator>Steven Nguyen</dc:creator>
      <pubDate>Thu, 09 Oct 2025 03:21:19 +0000</pubDate>
      <link>https://dev.to/steven_nguyen/why-spring-boot-kafka-oracle-and-tomcat-still-power-the-enterprise-in-2025-2pie</link>
      <guid>https://dev.to/steven_nguyen/why-spring-boot-kafka-oracle-and-tomcat-still-power-the-enterprise-in-2025-2pie</guid>
      <description>&lt;p&gt;Every few months, new frameworks, databases, and cloud platforms appear — each promising to “redefine” backend development.&lt;br&gt;
But while the tech world keeps evolving, some technologies quietly continue to &lt;strong&gt;run the backbone of global enterprises&lt;/strong&gt; — handling billions of transactions every day.&lt;/p&gt;

&lt;p&gt;I’m talking about the &lt;strong&gt;classic, battle-tested stack&lt;/strong&gt;:&lt;br&gt;
&lt;strong&gt;Spring Boot&lt;/strong&gt;, &lt;strong&gt;Kafka&lt;/strong&gt;, &lt;strong&gt;Oracle Database&lt;/strong&gt;, and &lt;strong&gt;Tomcat&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;After years of building and maintaining large-scale enterprise systems, I’ve realized that this combination remains one of the &lt;strong&gt;most stable, secure, and scalable foundations&lt;/strong&gt; you can rely on.&lt;/p&gt;




&lt;h2&gt;
  
  
  💡 The Enterprise Reality
&lt;/h2&gt;

&lt;p&gt;In startups, developers love to chase the “next big thing.”&lt;br&gt;
But in enterprise systems, reliability and maintainability matter more than trends.&lt;/p&gt;

&lt;p&gt;When your application handles financial transactions, supply chain data, or vendor operations across multiple regions, you can’t afford unstable frameworks or unproven tech stacks.&lt;/p&gt;

&lt;p&gt;Enterprises need:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Predictable performance&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Long-term support&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;High availability and security&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Integration with existing systems&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;That’s where &lt;strong&gt;Spring Boot + Kafka + Oracle + Tomcat&lt;/strong&gt; shine.&lt;/p&gt;




&lt;h2&gt;
  
  
  ⚙️ Why This Stack Still Works
&lt;/h2&gt;

&lt;h3&gt;
  
  
  🧩 1. Spring Boot — The Heart of Enterprise Java
&lt;/h3&gt;

&lt;p&gt;Spring Boot has redefined how Java applications are built.&lt;br&gt;
It gives you a clean structure, dependency injection, and ready-to-use integrations for REST APIs, security, messaging, and database access.&lt;/p&gt;

&lt;p&gt;With minimal setup, you get:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Auto-configuration for faster development&lt;/li&gt;
&lt;li&gt;Built-in health checks, metrics, and monitoring&lt;/li&gt;
&lt;li&gt;Seamless integration with Kafka, Oracle, and external APIs&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Spring Boot brings &lt;strong&gt;modern simplicity to the classic Java ecosystem&lt;/strong&gt; — a perfect blend of innovation and reliability.&lt;/p&gt;




&lt;h3&gt;
  
  
  ⚡ 2. Apache Kafka — The Data Nervous System
&lt;/h3&gt;

&lt;p&gt;In modern enterprise architecture, data moves fast — between microservices, analytics platforms, and third-party systems.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Kafka&lt;/strong&gt; acts as the real-time data backbone.&lt;br&gt;
It’s not just a message queue — it’s a distributed streaming platform that enables event-driven architecture at scale.&lt;/p&gt;

&lt;p&gt;With Kafka, you can:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Stream data between services reliably&lt;/li&gt;
&lt;li&gt;Decouple producers and consumers for scalability&lt;/li&gt;
&lt;li&gt;Handle millions of messages per second with low latency&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Spring Boot integrates natively with Kafka, allowing developers to produce and consume messages effortlessly with annotations and configuration.&lt;/p&gt;




&lt;h3&gt;
  
  
  🗄️ 3. Oracle Database — The Backbone of Enterprise Data
&lt;/h3&gt;

&lt;p&gt;Despite the rise of NoSQL and cloud-native databases, &lt;strong&gt;Oracle&lt;/strong&gt; continues to dominate mission-critical enterprise systems.&lt;/p&gt;

&lt;p&gt;Why?&lt;br&gt;
Because it offers:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Strong ACID compliance&lt;/li&gt;
&lt;li&gt;High performance for complex transactions&lt;/li&gt;
&lt;li&gt;Advanced security and backup mechanisms&lt;/li&gt;
&lt;li&gt;Mature support for PL/SQL, triggers, and stored procedures&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In enterprises where &lt;strong&gt;data consistency and security are non-negotiable&lt;/strong&gt;, Oracle remains unmatched.&lt;/p&gt;

&lt;p&gt;Spring Data JPA and Oracle JDBC drivers make integration smooth, allowing developers to write clean, maintainable repository layers without losing control over queries.&lt;/p&gt;




&lt;h3&gt;
  
  
  🌐 4. Tomcat — The Reliable Application Engine
&lt;/h3&gt;

&lt;p&gt;In an era of Docker and serverless deployment, you might think Tomcat is outdated.&lt;br&gt;
But in reality, &lt;strong&gt;Tomcat remains one of the most widely used servlet containers in the world&lt;/strong&gt; — and for good reason.&lt;/p&gt;

&lt;p&gt;It’s lightweight, easy to configure, and proven in production.&lt;br&gt;
Many Spring Boot applications are still deployed as WAR files or run embedded Tomcat instances — powering enterprise intranets, vendor portals, and public APIs across the globe.&lt;/p&gt;

&lt;p&gt;Tomcat’s strength lies in its &lt;strong&gt;stability, simplicity, and predictability&lt;/strong&gt;.&lt;br&gt;
It just works.&lt;/p&gt;




&lt;h2&gt;
  
  
  🧠 Why Enterprises Stick With This Stack
&lt;/h2&gt;

&lt;p&gt;Because it’s &lt;strong&gt;battle-tested&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;This stack has powered everything from banking systems to manufacturing ERP platforms to global logistics networks for over a decade.&lt;br&gt;
It’s not flashy, but it’s:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Stable under load&lt;/li&gt;
&lt;li&gt;Scalable across environments&lt;/li&gt;
&lt;li&gt;Supported by thousands of experienced engineers&lt;/li&gt;
&lt;li&gt;Backed by years of tuning, monitoring, and proven performance metrics&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;In other words — it’s &lt;strong&gt;trusted&lt;/strong&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  🚀 The Modern Twist
&lt;/h2&gt;

&lt;p&gt;The best part?&lt;br&gt;
This traditional stack isn’t frozen in time.&lt;/p&gt;

&lt;p&gt;Today, you can run:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Spring Boot microservices in Docker containers&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Kafka clusters on Kubernetes&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Oracle databases on cloud infrastructure (OCI, AWS, Azure)&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Tomcat services with CI/CD pipelines and modern observability&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;It’s a &lt;strong&gt;hybrid modernization&lt;/strong&gt; — the same solid foundation, adapted for the cloud era.&lt;/p&gt;




&lt;h2&gt;
  
  
  💬 Final Thoughts
&lt;/h2&gt;

&lt;p&gt;Technology will keep evolving, but &lt;strong&gt;enterprise systems thrive on trust, consistency, and scalability&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;And that’s exactly what &lt;strong&gt;Spring Boot + Kafka + Oracle + Tomcat&lt;/strong&gt; deliver.&lt;/p&gt;

&lt;p&gt;They’re not the newest tools in the toolbox — but they’re the ones you can build empires on.&lt;/p&gt;

&lt;p&gt;In the end, it’s not about using what’s trendy — it’s about using what &lt;strong&gt;works&lt;/strong&gt;.&lt;/p&gt;




&lt;p&gt;👨‍💻 &lt;em&gt;Written by Steven Nguyen&lt;/em&gt;&lt;br&gt;&lt;br&gt;
Senior Solution Architect | Building scalable enterprise systems with Spring Boot, Kafka, Oracle, and Tomcat.&lt;/p&gt;

</description>
      <category>oracle</category>
      <category>springboot</category>
      <category>java</category>
      <category>architecture</category>
    </item>
    <item>
      <title>Building a Real-Time Spreadsheet App with React, NestJS</title>
      <dc:creator>Steven Nguyen</dc:creator>
      <pubDate>Thu, 09 Oct 2025 00:39:02 +0000</pubDate>
      <link>https://dev.to/steven_nguyen/how-i-built-a-collaborative-excel-sheet-app-with-react-handsontable-nestjs-graphql-and-mongodb-4ah6</link>
      <guid>https://dev.to/steven_nguyen/how-i-built-a-collaborative-excel-sheet-app-with-react-handsontable-nestjs-graphql-and-mongodb-4ah6</guid>
      <description>&lt;p&gt;I’ve always loved the flexibility of Excel — but when teams need to collaborate in real time, spreadsheets can quickly become a mess of conflicting versions and broken formulas.  &lt;/p&gt;

&lt;p&gt;So I decided to build something different: a &lt;strong&gt;web-based collaborative spreadsheet app&lt;/strong&gt;, where multiple users can view and edit data directly from the browser — powered by &lt;strong&gt;React&lt;/strong&gt;, &lt;strong&gt;Handsontable&lt;/strong&gt;, &lt;strong&gt;NestJS&lt;/strong&gt;, &lt;strong&gt;GraphQL&lt;/strong&gt;, and &lt;strong&gt;MongoDB&lt;/strong&gt;.  &lt;/p&gt;

&lt;p&gt;This article walks you through the &lt;strong&gt;architecture&lt;/strong&gt;, &lt;strong&gt;setup&lt;/strong&gt;, and &lt;strong&gt;lessons learned&lt;/strong&gt; from building this project.&lt;/p&gt;




&lt;h2&gt;
  
  
  💡 The Goal
&lt;/h2&gt;

&lt;p&gt;The idea was simple:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;A web interface that feels like Excel
&lt;/li&gt;
&lt;li&gt;A backend API to handle CRUD operations
&lt;/li&gt;
&lt;li&gt;A database to persist sheet data
&lt;/li&gt;
&lt;li&gt;Real-time synchronization between users
&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  🧱 The Tech Stack
&lt;/h2&gt;

&lt;p&gt;Here’s what I chose and why:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;React + Handsontable&lt;/strong&gt; → To create a dynamic, spreadsheet-like UI
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;NestJS&lt;/strong&gt; → For a structured, TypeScript-based backend
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;GraphQL&lt;/strong&gt; → To efficiently fetch and mutate sheet data
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;MongoDB&lt;/strong&gt; → To store sheet contents and metadata flexibly
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This combination gives both speed and scalability — perfect for small SaaS apps or internal tools.&lt;/p&gt;




&lt;h2&gt;
  
  
  ⚙️ Step 1: Setting Up the Backend (NestJS + GraphQL + MongoDB)
&lt;/h2&gt;

&lt;p&gt;Create a new NestJS project:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm i &lt;span class="nt"&gt;-g&lt;/span&gt; @nestjs/cli
nest new excel-share-api
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Install dependencies:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; @nestjs/graphql @nestjs/apollo graphql apollo-server-express mongoose @nestjs/mongoose
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;app.module.ts&lt;/code&gt;&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Module&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@nestjs/common&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;GraphQLModule&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@nestjs/graphql&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;MongooseModule&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@nestjs/mongoose&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;SheetModule&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./sheet/sheet.module&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Module&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="na"&gt;imports&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
    &lt;span class="nx"&gt;GraphQLModule&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;forRoot&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
      &lt;span class="na"&gt;autoSchemaFile&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;playground&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;}),&lt;/span&gt;
    &lt;span class="nx"&gt;MongooseModule&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;forRoot&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mongodb://localhost:27017/excel_share&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
    &lt;span class="nx"&gt;SheetModule&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;AppModule&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  🧩 Step 2: Create a Sheet Schema and Resolver
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;sheet.schema.ts&lt;/code&gt;&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Prop&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Schema&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;SchemaFactory&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@nestjs/mongoose&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Document&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mongoose&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Schema&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;Sheet&lt;/span&gt; &lt;span class="kd"&gt;extends&lt;/span&gt; &lt;span class="nc"&gt;Document&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Prop&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="na"&gt;required&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt;
  &lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Prop&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="na"&gt;type&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;Object&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt;
  &lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;Record&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kr"&gt;any&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;SheetSchema&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;SchemaFactory&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;createForClass&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;Sheet&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;&lt;code&gt;sheet.resolver.ts&lt;/code&gt;&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight typescript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Resolver&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Query&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Mutation&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Args&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@nestjs/graphql&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;SheetService&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./sheet.service&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Sheet&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./sheet.model&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Resolver&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nx"&gt;Sheet&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;class&lt;/span&gt; &lt;span class="nc"&gt;SheetResolver&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nf"&gt;constructor&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;private&lt;/span&gt; &lt;span class="nx"&gt;sheetService&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;SheetService&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;

  &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Query&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;Sheet&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
  &lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="nf"&gt;sheets&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;sheetService&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;findAll&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Mutation&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nx"&gt;Sheet&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="nf"&gt;updateSheet&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Args&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;id&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;@&lt;/span&gt;&lt;span class="nd"&gt;Args&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;data&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kr"&gt;string&lt;/span&gt;
  &lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="k"&gt;this&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;sheetService&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;update&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;JSON&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;parse&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&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;Now your backend is ready to query and update spreadsheet data in MongoDB through GraphQL.&lt;/p&gt;




&lt;h2&gt;
  
  
  💻 Step 3: Building the Frontend (React + Handsontable + Apollo Client)
&lt;/h2&gt;

&lt;p&gt;Create the React app and install dependencies:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npx create-react-app excel-share-frontend
npm &lt;span class="nb"&gt;install &lt;/span&gt;handsontable @handsontable/react @apollo/client graphql
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;ExcelSheet.js&lt;/code&gt;&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;React&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;useState&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;useEffect&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;react&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;HotTable&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@handsontable/react&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;useQuery&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;useMutation&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;gql&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@apollo/client&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;GET_SHEET&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;gql&lt;/span&gt;&lt;span class="s2"&gt;`
  query {
    sheets {
      _id
      name
      data
    }
  }
`&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;UPDATE_SHEET&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;gql&lt;/span&gt;&lt;span class="s2"&gt;`
  mutation UpdateSheet($id: String!, $data: String!) {
    updateSheet(id: $id, data: $data) {
      _id
      name
      data
    }
  }
`&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;ExcelSheet&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;data&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;useQuery&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;GET_SHEET&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;updateSheet&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;useMutation&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;UPDATE_SHEET&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;sheetData&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;setSheetData&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;useState&lt;/span&gt;&lt;span class="p"&gt;([]);&lt;/span&gt;

  &lt;span class="nf"&gt;useEffect&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;data&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;sheets&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;length&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nf"&gt;setSheetData&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;sheets&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;].&lt;/span&gt;&lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;]);&lt;/span&gt;

  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;handleChange&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;async &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;changes&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;source&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;source&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;loadData&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;return&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nf"&gt;updateSheet&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
      &lt;span class="na"&gt;variables&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;sheets&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;].&lt;/span&gt;&lt;span class="nx"&gt;_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="na"&gt;data&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;JSON&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;stringify&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;sheetData&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
      &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="p"&gt;});&lt;/span&gt;
  &lt;span class="p"&gt;};&lt;/span&gt;

  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;h2&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;?.&lt;/span&gt;&lt;span class="nx"&gt;sheets&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;]?.&lt;/span&gt;&lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;h2&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;HotTable&lt;/span&gt;
        &lt;span class="na"&gt;data&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;sheetData&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;colHeaders&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;rowHeaders&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;afterChange&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;handleChange&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;licenseKey&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"non-commercial-and-evaluation"&lt;/span&gt;
      &lt;span class="p"&gt;/&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="nx"&gt;ExcelSheet&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now you have a live spreadsheet UI that syncs changes through GraphQL to MongoDB.&lt;/p&gt;




&lt;h2&gt;
  
  
  ⚡ Step 4: Adding Real-Time Collaboration (Optional)
&lt;/h2&gt;

&lt;p&gt;To make it collaborative, integrate &lt;strong&gt;GraphQL Subscriptions&lt;/strong&gt; or &lt;strong&gt;WebSockets&lt;/strong&gt; in NestJS.&lt;br&gt;&lt;br&gt;
Each time a user updates a cell, broadcast that update to all connected clients.&lt;/p&gt;

&lt;p&gt;Example setup:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Use &lt;code&gt;@nestjs/websockets&lt;/code&gt; for socket updates
&lt;/li&gt;
&lt;li&gt;Broadcast using &lt;strong&gt;Socket.io&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;On the frontend, listen for events and refresh the table
&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  🧠 Lessons Learned
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;Handsontable is powerful — but you must handle performance when data grows.
&lt;/li&gt;
&lt;li&gt;GraphQL fits perfectly for partial data updates and flexible queries.
&lt;/li&gt;
&lt;li&gt;MongoDB’s document model makes it easy to store dynamic sheet data.
&lt;/li&gt;
&lt;li&gt;Clear data versioning and change tracking are critical for collaboration.
&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  🚀 Final Thoughts
&lt;/h2&gt;

&lt;p&gt;Building an Excel-like collaboration tool is challenging but rewarding.&lt;br&gt;&lt;br&gt;
With &lt;strong&gt;React&lt;/strong&gt;, &lt;strong&gt;NestJS&lt;/strong&gt;, &lt;strong&gt;GraphQL&lt;/strong&gt;, and &lt;strong&gt;MongoDB&lt;/strong&gt;, you can achieve both &lt;strong&gt;flexibility and performance&lt;/strong&gt; — and Handsontable gives your users the familiar spreadsheet experience they love.&lt;/p&gt;

&lt;p&gt;This setup can easily become the foundation for:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Internal business tools
&lt;/li&gt;
&lt;li&gt;Data analysis dashboards
&lt;/li&gt;
&lt;li&gt;Lightweight SaaS spreadsheet applications &lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;All running with &lt;strong&gt;one unified stack — TypeScript end to end.&lt;/strong&gt;&lt;/p&gt;




&lt;p&gt;👨‍💻 Written by Steven Nguyen — Engineering Manager | Building scalable enterprise systems with Java, NestJS, and modern DevOps practices.&lt;/p&gt;

</description>
      <category>react</category>
      <category>javascript</category>
      <category>tutorial</category>
      <category>fullstack</category>
    </item>
  </channel>
</rss>
