Visual Guide to TCP at the Transport Layer


I built a detailed visual diagrams for the Transmission Control Protocol (TCP) — one of the core protocols powering the internet, that operates at the Transport Layer (Layer 4) of the OSI model.

I broke down:
🔹 TCP Segment Structure: –
Source & destination ports
Sequence number
Acknowledgment number
Flags (SYN, ACK, FIN, RST, PSH, URG)
Window size
Checksum
Options & payload
Here the full animated diagram svg link of TCP structure: – https://github.com/knkrn5/Programming-Concepts/blob/main/computer-networking/protocols/transmission-control-protocol/TCP-segment/tcps.svg


🔹 TCP 3-Way Handshake: –
SYN
SYN-ACK
ACK
Sequence & acknowledgment numbers
Window size negotiation
MSS negotiation
How a connection becomes ESTABLISHED
Here the full animated diagram svg link of TCP handshake: – https://github.com/knkrn5/Programming-Concepts/blob/main/computer-networking/protocols/transmission-control-protocol/tcp-handshake/tcph.svg

While studying networking, I realized many resources explain TCP theoretically but not visually.
So I created these diagrams to make the packet flow and header fields easier to understand step-by-step.

One thing I found especially interesting:
TCP reliability is achieved through sequence numbers, acknowledgments, retransmissions, and flow control — all working together behind the scenes every time we browse a website or send data online.

Understanding protocols at this level really changes how you see networking and distributed systems.

Infrastructure as Vibe: What Comes After Infrastructure as Code

A friend of mine sent me a screenshot last week. Eight tabs. Vercel, Neon, Cloudflare, GitHub, Stripe, Resend, a Notion doc with env vars, and a terminal running ngrok. He was three hours into “just deploying a side project” and had not written a line of product code yet. The message under the screenshot said: “tell me again why this is the good timeline.”

I laughed because I have lived this exact afternoon at least fifty times. You know the stack you want. You know which buttons to press. The CLIs are great individually. None of them talk to each other. So you become the wetware integration layer, copying connection strings into env files, pasting CNAME records into DNS panels, remembering which secret needs to be rotated where.

That experience is the friction that gave the next paradigm its name. Infrastructure as Vibe. The phrase started as a joke on Twitter, but enough people stopped laughing for it to become a real category. Neon’s official account endorsed it on stage. Cloudflare’s team has been hinting at it in every product update for six months. The pattern is showing up everywhere even when people do not use the term.

This article is about what “infrastructure as vibe” actually means as a paradigm, why it became inevitable, what it gets right, what it gets dangerously wrong, and where developer tooling is heading because of it.

From Infrastructure as Code to Infrastructure as Vibe

To understand why this matters, you have to remember what each previous layer was a reaction to.

In the early 2010s, deploying anything to production meant clicking through AWS consoles, SSHing into boxes, and praying you remembered to set the security group correctly. People called this ClickOps. It was a disaster for reproducibility. You could not version it. You could not review it. The person who set it up was the only one who knew what it looked like, and the moment they left the company, the infrastructure became a haunted house.

Infrastructure as Code was the response. Terraform, CloudFormation, later Pulumi and CDK. Declare your infrastructure in a file. Commit the file to git. Run a command. Get the same environment every time. Everyone who has ever maintained a real system understands why this was a good idea.

But IaC carried a tax that nobody really wanted to pay. You now had to learn HCL, or YAML schemas, or a TypeScript-flavored DSL that pretended to be regular code but very much was not. You had to keep state files. You had to understand provider versions. You had to debug why your apply hung for nineteen minutes because someone deleted a resource in the console. You had to write 400 lines of config to deploy something that, in your head, was “a Node app and a Postgres database.”

GitOps, Helm charts, and Kubernetes operators were attempts to make this nicer. They mostly added more files to learn. Then PaaS providers like Heroku, Vercel, Render, Railway, and Fly came back into fashion because they let you skip most of that. The pattern was “git push and we figure it out.” That worked great until you wanted to do anything slightly outside the happy path. As soon as you needed a database in a different region, or a queue that talked to a worker, or a domain that pointed at two services, you were back in five dashboards.

Infrastructure as Vibe is the layer that sits on top of all of this. The interface is plain language. The implementation is “we figure out the right APIs to call.” You describe what you want in the way you would describe it to a colleague who happens to know every platform’s quirks. The system reads your intent, scans your code, makes opinionated choices, and shows you what it provisioned.

If IaC was about removing humans from the imperative step, Infrastructure as Vibe is about removing humans from the declarative step too. You stop writing configuration entirely. You write intent.

What “Infrastructure as Vibe” Actually Means

The phrase is catchy enough that people are already using it to mean different things, so let me be specific about what it actually describes as a paradigm.

There are three properties that have to be true for a tool to fit this category.

The interface is natural language, not configuration. You do not fill out a form. You do not edit a YAML file. You type or say what you want. “Deploy this repo. Add a Postgres. Point it at myapp.com.” The system parses that, infers the gaps, and confirms before doing anything destructive.

Inference replaces declaration. Traditional IaC requires you to specify every detail because the tool refuses to assume. Infrastructure as Vibe inverts that. The tool reads your code, your dependencies, your existing project, and makes structural assumptions based on what it sees. If your package.json includes prisma and pg, you probably want Postgres. If you have @supabase/supabase-js, you probably want Supabase. If you have mongoose, you want Mongo. You can override anything, but the default is “guess correctly most of the time.”

The platform absorbs the integration work. This is the part that distinguishes Vibe from “just a wrapper over Terraform.” A real Infrastructure as Vibe tool does not just generate config and hand it back. It calls the APIs, watches the rollout, handles the failure modes, retries the flaky ones, and tells you when it is done. You do not get a 200-line plan to apply yourself. You get a result.

You can argue about whether all three need to be present. I would say yes, because if you remove any of them, you collapse back into a previous paradigm. Strip the natural language and you have a smarter PaaS. Strip the inference and you have ChatOps that just calls a CLI. Strip the integration work and you have a clever assistant that drafts Terraform.

The combination is what makes it new. And the combination is what makes some developers nervous.

The Friction That Made This Inevitable

You can see the demand for this paradigm if you look at what developers actually complain about online. Not what they say in conference talks. What they post at 11pm on a Tuesday after their fifth deploy attempt.

The complaints cluster into a few categories that should be familiar to anyone who has shipped a side project in the last three years.

Tab fatigue. Every PaaS has a console. Every database has a console. Every domain registrar has a console. Every observability tool has a console. You are not really using each one. You are using all of them as a single distributed system that someone forgot to integrate.

Bill shock. This is the most consistent complaint across Vercel, Render, Neon, Supabase, and Fly. Usage meters that run while you sleep. No hard caps. You read a forum post in the morning explaining that someone got a $4,000 bill because their cron job hit an infinite loop. You spend the next hour wiring spend alerts and budget guards. That hour is not building product.

Secret sprawl. A modern app has, on average, somewhere between twelve and twenty environment variables across staging and production. You set them in three different dashboards. You forget which is which. You leak one into a screenshot during a demo. You promise yourself you will rotate them later. You do not.

DNS purgatory. You buy a domain. You point it at a service. The TTL is 24 hours and the CNAME is fighting an A record. You verify ownership through a TXT record that takes 45 minutes to propagate. You check dig in three terminals. You add a www subdomain and the redirect breaks. You forget to renew the cert. The cert renews automatically and you forget you ever worried about it.

None of these are theoretical. They are the unpaid labor of being a modern developer. Every one of them is something a sufficiently smart tool could absorb. The reason none of them got fully absorbed sooner is that no single platform owned the whole stack. Vercel cannot fix your Neon bill. Neon cannot fix your DNS. Your DNS provider cannot fix your secret rotation. Somebody had to play orchestrator. Until recently, that somebody had to be you.

The shift toward natural language as a universal interface, combined with the agentic tooling I wrote about in agentic coding, changed the math. A coordination layer that calls every platform’s API on your behalf no longer needs to be a Heroku-scale company. It can be a relatively small orchestration service with good prompts, good defaults, and a careful integration layer.

That is why this paradigm is showing up now and not five years ago.

Where You Can Already See It

You can spot Infrastructure as Vibe in the wild even when nobody is calling it that.

When Vercel added “deploy from a screenshot” and “deploy from a sentence” via v0, that was the paradigm leaking into a frontend product. You did not configure anything. You described something. The platform figured out the rest.

Cloudflare has been pushing in the same direction with their AI gateway and their increasingly chat-driven control plane. You can describe a worker, get a worker, attach a domain, all without ever opening a config file. They are not marketing it as “infrastructure as vibe,” but the shape of the experience is unmistakable.

Render’s blueprints have been quietly turning into something similar. Drop a repo in, accept the inferred services, click deploy. The friction between “I have an idea” and “it is live on the internet” gets compressed every release.

The most aggressive version of this is what is happening through coding agents themselves. Claude Code, Cursor agents, and the various MCP-driven orchestrators can now provision a database, push a deploy, configure a domain, and rotate a secret from a single prompt, given the right tools. The “infrastructure” is the LLM’s tool calls. The “vibe” is the prompt. It looks weird the first time you see it. The second time it looks inevitable.

There are also a wave of newer tools whose entire pitch is the paradigm. Some are general purpose orchestrators. Some are stack-specific. Some are aimed at non-technical founders who never wanted to learn the difference between an A record and a CNAME. The tools differ. The pattern does not.

If you squint, you can also see this pattern in adjacent categories. Stripe Apps and shadcn/ui blocks both reduce the cognitive load of “I need this thing” to a one-line invocation. They are not infrastructure, but they share the same posture: assume good defaults, do the integration work for me, let me describe outcomes instead of steps.

Why Developers Resist It

This paradigm is not universally welcomed, and the resistance is not stupid. Most of it comes from real scars.

Loss of control. A developer who has been burned by a magical platform will be suspicious of any tool that says “trust me, I will figure it out.” They want to see the plan. They want to read the Terraform. They want to know what the security group looks like. The Vibe layer hides that by default, and that is the right design choice for most users and the wrong choice for some.

Black box anxiety. When something breaks at 3am, you need to know what got provisioned, where, with what permissions. If the provisioning happened through a chat interface and the audit log is “Claude decided,” that is not a debugging story. That is an incident report you have to write to your CTO.

Comprehension debt. I wrote about this in the vibe coding revolution in the context of code. It applies just as forcefully to infrastructure. The developer who never learned what a security group is, because a friendly tool always set it up correctly, is going to have a bad time the first time the tool gets it wrong. And the tool will eventually get it wrong, because every tool does.

Vendor lock-in. A coordination layer that owns your deploy, your database, your DNS, and your secrets is also a single point of failure for your entire stack. If the company behind it gets acquired, raises prices, or pivots, you may not have an exit strategy. IaC at least gave you portable files. Vibe gives you outcomes that are difficult to reproduce on a different platform without redoing the work.

Existing skill obsolescence. A developer who spent five years getting good at Terraform is not enthusiastic about a paradigm that says the Terraform expertise is now a niche specialty. This is a human reaction, not a technical one, but it shapes adoption.

These are all legitimate concerns. The right response to them is not “trust the magic.” It is to design Vibe tooling that surfaces the underlying reality on demand. Show me what got created. Show me the cost projection. Show me where to override. Give me an escape hatch back to raw config. The good versions of this paradigm will be the ones that respect the people who want to look under the hood.

When Infrastructure as Vibe Works and When It Fails

Like every paradigm before it, this one has a fitness landscape. It is not universally better. It is meaningfully better in some places and meaningfully worse in others.

It works great for:

  • Side projects and prototypes. The whole point is getting from idea to live URL in minutes. The cost of being wrong is low. The cost of being slow is the project dying before launch.
  • Solo developers and small teams. The integration work is a tax that hurts small teams the hardest. Removing it gives them back a measurable percentage of their week.
  • Greenfield production apps with standard stacks. If you are building a Next.js app with Postgres and Stripe and Resend, the default choices a Vibe tool would make are probably the same choices you would have made.
  • Founders and designers without a dedicated devops person. The alternative is hiring someone or hand-waving DNS for a year. This is a real, expensive choice that this paradigm collapses.

It is risky for:

  • Regulated environments. Healthcare, fintech, public sector. You need explicit, auditable, declared infrastructure for compliance reasons. Vibe-style provisioning is not yet the right shape for SOC 2 audits, even though it can in principle generate the artifacts.
  • Large existing systems. A coordination layer that is good at clean deploys is not necessarily good at integrating with a fifteen-year-old VPC, three legacy databases, and a custom IAM model. The brownfield problem is brutal.
  • Mission-critical production with hard SLOs. When 99.95% matters, you cannot afford “the platform chose for me.” You need to make every choice deliberately and review it.
  • Anyone who hates leaky abstractions more than they hate friction. Some developers are wired to want to see the bytes. They will be miserable on top of a Vibe layer no matter how well it works.

The honest version of this paradigm acknowledges those tradeoffs instead of pretending the line is everywhere. You can use Infrastructure as Vibe to ship a prototype in an afternoon and still believe that your bank should run on hand-written Terraform. Both of those statements can be true at the same time.

The Vibe Stack Underneath

Let me get a little more concrete about how this actually works under the hood, because “the AI does it” is not a real answer.

Most viable Infrastructure as Vibe systems sit on top of a layer cake that looks something like this.

Deterministic detection comes first. You do not ask the LLM what database to provision. You scan the package.json, the lockfile, the go.mod, the Cargo.toml. You read framework signatures from imports. You check for known config files. This is fast, free, and reliable. The LLM only gets called when the deterministic layer is genuinely ambiguous.

Intent parsing is where the LLM earns its keep. Translating “deploy this and add a database, point it at app.example.com” into structured calls is exactly the kind of task small fast models like Claude Haiku are good at. The output is not freeform. It is a constrained schema that the orchestrator can execute. No code generation. No hallucinated APIs. Just structured decisions.

Orchestration is plain old engineering. A long-running service, a job queue, a Redis somewhere, and careful integration code that knows how every target platform actually behaves. This is the part that takes the longest to get right and is the hardest to fake with a demo. Anyone can ship “I called the API.” Far fewer people ship “I called the API, handled the rate limit, retried the flaky one, rolled back the partial state when the third call failed, and gave you a useful error message.”

Cost transparency lives in the middle. Before anything destructive happens, the system tells you what it is about to do and what it estimates the monthly cost will be. This is the answer to bill shock and it is what separates a serious Vibe tool from a fancy CLI wrapper.

Audit logging is the floor. Every provisioned resource, every config decision, every secret rotation gets logged with timestamps, model versions, and the original prompt. When something breaks, you need to be able to reconstruct exactly what happened. The version of this paradigm that does not log carefully will not survive contact with real users.

The reason this stack matters is that it shows the paradigm is not “vibes all the way down.” Most of it is conventional, careful software engineering. The vibe is at the surface. The substrate is the same kind of integration work that has always been required to make platforms talk to each other. The trick is that the substrate is finally getting built, because the surface is finally compelling enough to justify the investment.

What Has to Be True for This to Actually Work

Predictions are cheap. Let me make some falsifiable ones.

For Infrastructure as Vibe to graduate from “interesting demo” to “default way most apps get deployed in 2028,” a few conditions have to hold.

Reversibility has to be cheap. If I can ask the system to provision something and then ask it to undo cleanly, I will use it. If undoing requires me to log into five dashboards and clean up orphans, I will not trust it again. The good tools will make destroy as fluent as create.

Cost has to be visible before action. Every command that costs money should show its cost first. Every recurring resource should show its monthly projection. This is non-negotiable. Bill shock is the single biggest reason people abandon PaaS, and any Vibe layer that does not solve it is one bad incident away from a viral horror story.

Audit has to be ambient. Not a feature you turn on. Always on by default. Every action provenanced. Every secret rotation recorded. The audit log is what unlocks regulated use cases later.

The escape hatch has to be real. “Export to Terraform” or “show me the underlying calls” cannot be a roadmap item. It is the price of trust. If a developer feels trapped, they will not adopt. If they can leave, they probably will not.

Defaults have to be opinionated, not naive. A tool that asks me twelve questions is worse than the dashboard it replaces. A tool that picks reasonable answers and lets me override is the entire point. The opinions need to be good ones, which means real product decisions, not arbitrary ones.

If those conditions hold, the paradigm wins for most new applications. If they do not, this becomes another era of demos that did not generalize. Both outcomes are plausible. I am betting on the first one because the underlying technology curve, particularly the cost and reliability of structured LLM output, is moving in the right direction every quarter.

Where This Goes Next

I keep thinking about how this connects to the broader shift toward spec-driven development. In code, the spec is becoming the source of truth and the code is generated from it. In infrastructure, the intent is becoming the source of truth and the config is generated from it. Same pattern, different layer. The end state is that human-written declarative config might become as rare as hand-written assembly is today. It will still exist for the cases that need it. It will not be the default.

The teams that move fastest will be the ones who treat infra as a means, not as a craft. Not because the craft does not matter, but because most of the time, the right amount of craft to apply to “ship this prototype tonight” is none. The same developer who insists on hand-tuned config for a financial service will happily let the Vibe layer handle their weekend project. That bifurcation is the natural shape of the next few years.

The risk worth watching is consolidation. A handful of companies will become the orchestration layer between all the platforms. They will know what you deploy, what you spend, what you store, and where your traffic comes from. That is enormous power. The paradigm only works socially if the tools at the surface compete hard enough that no single one becomes the lock-in story for the entire web.

I also expect this to push the underlying platforms toward better, more predictable APIs. If your value as a database, hosting provider, or DNS service is increasingly mediated through an orchestration layer, your API ergonomics matter more than your dashboard ergonomics. That should be good for everyone. The platforms with the cleanest APIs are about to win an asymmetric amount of new business.

The interesting question for the next few years is which of the giant providers, the existing PaaS players, or the newer orchestration startups end up owning the surface. I do not know the answer. I do know the surface is moving from forms to sentences, and from documents to conversations, and that is not going back.

My Take

I have been deploying things for most of a decade. I have written more Terraform than I want to admit. I have set up Vercel projects in my sleep. I know the muscle memory. I am still tired of doing it.

The honest reason Infrastructure as Vibe is going to win for most use cases is not that the technology is magical. It is that the alternative is bad. Modern application infrastructure asks every developer to be a part-time platform engineer. That was tolerable when there were three platforms. It is not tolerable when there are thirty. The integration work has gotten worse every year, and developers have absorbed it because there was no other option. Now there is one.

The version of this paradigm that fails is the one that hides too much. Black-box magic that you cannot inspect, cannot reverse, cannot afford to break. That version will get one good demo cycle and then a thread of horror stories that kill it. The version that wins is the one that defaults to friction-free and treats the underlying truth as something you can always pull up. Good defaults, visible cost, clean audit, easy exit.

If you are building developer tools, the lesson is to take the integration work seriously even when the surface looks easy. The fluency of the chat interface is the marketing. The brittleness of the third API call you make under the hood is the product. The companies that win this category will be the ones that obsess over the unsexy substrate.

If you are a developer who has resisted this paradigm, I would not blame you. Most prior “we make infrastructure easy” pitches were wishful thinking. This one feels different because the AI layer makes the inference step finally cheap, and the existing platform CLIs are finally good enough to chain reliably. The two missing pieces showed up at the same time.

Infrastructure as Code did not kill the console. PaaS did not kill IaC. Infrastructure as Vibe will not kill PaaS. Every layer continues to exist. The default just moves up. The thing you reach for first when you start a new project keeps getting closer to “here is what I want to build.” That progression is the whole story of developer tooling. Vibe is the next stop on a road we have been walking for thirty years.

I will keep my Terraform skills sharp. I will also keep typing sentences and watching apps appear. Both of those can be professional. Pretending only one of them is, at this point, is just nostalgia in a hoodie.

I built my own uptime monitor because UptimeRobot felt cluttered – here’s what I learned

I built my own uptime monitor because UptimeRobot felt cluttered — here’s what I learned

The problem

I’ve been using UptimeRobot for a while. It works, but every time I opened it I felt like I was looking at a dashboard designed for enterprise teams. I just wanted to know: is my site up? If not, tell me. That’s it.

So I built my own.

What I built

PingBoard — uptime monitoring with public status pages. Monitors URLs on a schedule, sends alerts when things go down, and generates a clean shareable status page for your users.

5 monitor types: HTTP, keyword, DNS, API, and heartbeat.

The stack

  • Next.js 14 App Router + TypeScript
  • Convex — backend, DB, cron jobs, realtime subscriptions
  • Clerk — auth
  • Resend — email alerts
  • Lemon Squeezy — payments (Stripe isn’t available in India)
  • Framer Motion — animations

The interesting parts

Realtime status pages without WebSockets

Convex’s reactive queries mean the public status page updates instantly when a monitor goes down — no polling, no manual WebSocket management. Just a useQuery hook and it works.

The ping loop

A Convex cron fires every 30 seconds, finds monitors that are due for a check, and schedules individual check actions per monitor. Each check runs independently — one slow site doesn’t block others.

Heartbeat monitoring

Instead of PingBoard pinging your service, your service pings PingBoard. Useful for cron jobs and background workers. If PingBoard doesn’t hear from your job within the expected interval × 1.5, it opens an incident.

Payments from India

Stripe isn’t available in India so I went with Lemon Squeezy. Acts as merchant of record — handles VAT, GST, tax compliance automatically. Checkout was live in a day.

What I’d do differently

  • Started with Convex from day one — initially considered Supabase but switched early and never looked back
  • Underestimated how much time auth takes — Clerk saved probably 2 weekends
  • Should have verified the Resend domain earlier (still in sandbox mode — alerts only reach verified addresses)

Where it is now

Live at ping-board-monitor.vercel.app. Free tier, no credit card. Built for myself, a friend convinced me to open it up.

Would love feedback — especially from devs who’ve felt the same frustration with existing tools.

GraphQL là gì — Tại sao nên dùng cho Social App?

GraphQL là gì — Tại sao nên dùng cho Social App?

1. GraphQL là gì?

GraphQL là ngôn ngữ truy vấn cho API, do Facebook phát triển năm 2015. Thay vì server quyết định bạn nhận được gì, client tự chỉ định chính xác dữ liệu mình cần.

So sánh nhanh với REST

REST GraphQL
Endpoint Nhiều (/users, /posts…) Chỉ 1 (/graphql)
Dữ liệu trả về Fixed, server quyết định Linh hoạt, client quyết định
Over-fetching Thường xuyên Không bao giờ
Under-fetching Phải gọi nhiều request Lấy 1 lần được hết

3 khái niệm cốt lõi

  • Query — đọc dữ liệu (như GET)
  • Mutation — thay đổi dữ liệu (như POST/PUT/DELETE)
  • Subscription — lắng nghe realtime (như WebSocket)

2. Tại sao GraphQL phù hợp với Social App?

2.1 Một request — render cả trang

Feed social cần render cùng lúc: avatar, tên user, ảnh post, số like, top comment…

REST: 4–5 request tuần tự hoặc song song

GET /feed
GET /users/:id
GET /posts/:id/likes
GET /posts/:id/comments

GraphQL: 1 request duy nhất, server tự resolve

query Feed {
  feed {
    author { avatar name isFollowing }
    content images
    likes { count isLikedByMe }
    topComments { text author { name } }
  }
}

→ Giảm latency, giảm round-trip, render nhanh hơn rõ rệt.

2.2 Lấy đúng field cần — không thừa, không thiếu

Màn hình khác nhau → nhu cầu data khác nhau:

Màn hình Cần gì
Feed (thumbnail) name, avatar, title, likeCount
Post detail thêm fullContent, comments, shares
Profile card chỉ name, avatar, followerCount

REST trả về cùng 1 response nặng cho tất cả. GraphQL cho phép mỗi screen query đúng field nó cần — đặc biệt quan trọng với mobile, tiết kiệm bandwidth đáng kể.

2.3 Frontend không cần “gom” data từ nhiều API

REST — FE phải tự join và normalize:

const user = await getUser(id)
const posts = await getPosts(id)
const followers = await getFollowers(id)

// Rồi tự map, merge...
const profileData = mergeAndNormalize(user, posts, followers)

GraphQL — server chịu trách nhiệm resolve mọi relationship, FE nhận về 1 object sẵn sàng dùng. Logic mapping nằm ở tầng resolver thay vì rải rác ở từng màn hình.

2.4 Caching & Batching — xử lý data lặp lại thông minh

Social feed hay có pattern: cùng 1 user xuất hiện ở nhiều post.

DataLoader pattern tự động batch + deduplicate:

Post 1 → author_id: 42  ┐
Post 2 → author_id: 17  ├─ DataLoader → 1 DB query duy nhất
Post 3 → author_id: 42  ┘   SELECT * FROM users WHERE id IN (42, 17)

Client-side (Apollo/urql) cũng normalize cache theo object ID — user cập nhật avatar ở 1 chỗ, toàn bộ feed tự cập nhật, không cần refetch.

2.5 Self-documenting — FE tự khám phá API

GraphQL có Introspection tích hợp sẵn: schema chính là documentation. Công cụ như GraphiQL / Apollo Sandbox cho phép:

  • Autocomplete field khi gõ query
  • Xem type, mô tả của từng field ngay trong IDE
  • Không cần Postman collection hay Swagger riêng

→ FE và BE làm việc từ cùng 1 source of truth — schema file. Thêm field mới, FE thấy ngay.

3. Pain Point thực tế: /api/auth/me

Đây là ví dụ điển hình về vấn đề REST gặp phải trong production.

Hiện trạng — trả về “tất cả hoặc không có gì”

// GET /api/auth/me
{
  "id": 123456,
  "name": "Nguyễn Văn A",
  "avatar": "https://...",
  "coin": 45200,
  "rank": "GOLD",           // ❌ aggregate loyalty_histories
  "rankProgress": 78.5,     // ❌ tính toán nặng
  "totalEarned": 1250000,   // ❌ SUM toàn bộ lịch sử
  "totalSpent": 890000,     // ❌ SUM toàn bộ lịch sử
  "referralCount": 12,      // ❌ COUNT từ bảng referrals
  "taskCompletedCount": 47, // ❌ COUNT từ bảng task_points
  "badges": [...]           // ❌ JOIN thêm bảng badges
}

Mỗi lần app load → gọi /auth/me → server tính toán tất cả, dù màn hình chỉ cần hiện tên + avatar.

Phân tích chi phí thực tế

Field Chi phí server Tần suất FE dùng
name, avatar, coin Rất thấp Mọi màn hình
rank, rankProgress Nặng — aggregate loyalty_histories Chỉ màn hình Profile/Rank
totalEarned, totalSpent Nặng — SUM toàn lịch sử Chỉ màn hình Thống kê
referralCount Trung bình Chỉ màn hình Referral
taskCompletedCount Trung bình Chỉ màn hình Task
badges Nặng — multi JOIN Chỉ màn hình Profile

→ 90% request /auth/me chỉ cần 3–4 field đầu, nhưng vẫn phải trả tiền tính toán toàn bộ.

Với GraphQL — lazy computation theo từng màn hình

App header (render mọi lúc):

query AppHeader {
  me {
    name
    avatar
    coin      # query cực nhẹ, chỉ SELECT 3 fields
  }
}

Màn hình Profile/Rank (user chủ động vào):

query ProfileScreen {
  me {
    name avatar coin
    rank          # chỉ tính khi user thực sự mở màn hình này
    rankProgress
    badges
  }
}

Màn hình Thống kê (vào ít nhất):

query StatsScreen {
  me {
    totalEarned       # heavy computation chỉ chạy khi cần
    totalSpent
    referralCount
    taskCompletedCount
  }
}

Kết quả

REST hiện tại GraphQL
App header load ~150ms (tính toán full) ~8ms (chỉ SELECT 3 fields)
Profile/Rank ~150ms (dù không cần) ~120ms (lazy, chỉ khi vào)
Server load (600K users) Tính rank cho tất cả Chỉ tính khi được query

Heavy field như rank trở thành lazy resolver — không tốn tài nguyên tính toán cho 600K user mỗi khi họ mở app.

How I shipped my PWA to Google Play as a TWA (and what actually went wrong)

I built Money Me as a PWA. It works offline, it’s installable, it feels like a native app. At some point I decided to put it on Google Play because people kept asking “is it in the store?”

The TWA route seemed obvious. Wrap the existing PWA in an Android shell, ship it. I figured a day of work, maybe two.

It took me a lot longer than that.

So what is a TWA

A Trusted Web Activity is basically an Android app that opens your website in Chrome, but with the browser UI stripped away. No address bar, no back button. Fullscreen. If you didn’t know better you’d think it was a regular Android app.

The “trusted” bit: you prove you own the domain by putting a specific JSON file on your server. Android checks it against your app’s signing key. If it matches, Chrome hides the browser chrome (pun maybe intended). If it doesn’t match, you get an ugly blue bar at the top and your app looks like a glorified bookmark.

Important thing I didn’t understand at first: a TWA is NOT a WebView. It’s actual Chrome running your site. Service workers work, push notifications work, everything your PWA already does just… works. This is the main reason to use a TWA over something like Capacitor or a WebView wrapper.

Bubblewrap

Google has a tool called Bubblewrap that generates an Android project from your web manifest. Point it at your manifest URL, it spits out a project, you build an APK.

My advice: don’t treat it as a black box. You will need to open the generated project and mess with build.gradle and the Android manifest at some point. If you’ve never seen an Android project before, spend 20 minutes understanding the structure first. You’ll thank yourself later when something breaks and the error message means nothing to you.

The blue bar (aka my nemesis for two days)

This is where I lost the most time. The blue navigation bar shows up when Chrome can’t verify you own the domain. Your app still works fine underneath, it just looks terrible.

The fix is a file at /.well-known/assetlinks.json:

[{
  "relation": ["delegate_permission/common.handle_all_urls"],
  "target": {
    "namespace": "android_app",
    "package_name": "com.yourapp.twa",
    "sha256_cert_fingerprints": ["YOUR:SHA256:FINGERPRINT:HERE"]
  }
}]

Simple enough. Except I got the fingerprint wrong three times before figuring out what was happening.

The problem: you have multiple signing keys and they all have different fingerprints. There’s your local debug key, your upload key, and then Google Play’s own app signing key. Play App Signing is mandatory for new apps now, which means Google re-signs your bundle after you upload it. So the fingerprint that matters for asset links is Google’s key, not yours.

Go to Play Console → Setup → App signing → App signing key certificate and grab the SHA-256 from there. I wasted hours using my upload key fingerprint instead. The blue bar kept showing up and I kept double-checking the JSON format, the content type, the file path. The file was fine. The fingerprint was just wrong.

Other things that bit me:

Chrome caches the verification result. You fix the asset links file, reinstall the app, and… blue bar is still there. You need to clear Chrome’s data on the test device. Not just the cache. The data. I was clearing the app cache only and wondering why nothing changed.

Content-Type has to be application/json. My CDN was serving it as text/plain. Took me a while to catch that one.

Use Google’s verification tool. I should have used this from the start instead of guessing. It tells you exactly what’s wrong.

The signing key situation

If you’re a web developer, Android signing keys are confusing. There are two keys involved:

  1. Your upload key — you use this to sign the bundle before uploading to Play Console
  2. Google’s app signing key — Google uses this to sign the APK that actually gets distributed to users

For your asset links JSON, you need #2. Not #1. I keep repeating this because it took me an embarrassingly long time to figure out, and every tutorial I found either glossed over it or assumed you already knew.

Generate your upload key:

keytool -genkey -v -keystore upload-keystore.jks 
  -keyalg RSA -keysize 2048 -validity 10000 
  -alias upload

Then do your first upload to Play Console, and THEN go grab the app signing key fingerprint. You can’t get it before the first upload because Google generates it at that point.

Closed testing: the 12-tester gate

Once the app was building and the blue bar was gone, I thought I was done. Nope.

Google requires new apps to have 12 testers opted into a closed beta for 14 continuous days before you can go to production. You need real people with real Google accounts who join your testing program, install the app, and stay opted in for the full two weeks.

If you’ve got an existing user base, this is nothing. If you’re a solo dev shipping your first app, it’s a real bottleneck. I wrote a whole post about this already.

What I’d do differently next time

Get asset links working BEFORE you build the TWA. Host the JSON file, verify it with Google’s tool, confirm it’s correct. Then build the app. Debugging both at the same time is miserable.

Start looking for testers before your build is ready. The 14-day clock is the actual bottleneck, not the technical work.

Test on a Samsung phone early. My app looked perfect on a Pixel. Then I tried it on an older Galaxy and some things were off.

Is it worth it though?

Yeah. For a PWA that’s already working well, a TWA is the right call. One codebase, Play Store presence, native-feeling experience. The setup takes a weekend if you know the pitfalls. Compared to maintaining a separate React Native or Kotlin app? Not even a question.

The downside is you’re dependent on Chrome being installed, but that’s basically every Android phone. And you need to keep your asset links in sync when keys change. That’s about it.

I’m going through the closed testing process now with Money Me. If you’ve got an Android phone and don’t mind helping an indie dev clear the 12-tester gate, I’d massively appreciate it. Beta testers get 6 months of Premium free.

👉 Join the beta on Google Play

30 seconds to opt in. If you’ve got TWA questions, drop them in the comments — I’ve made most of the mistakes already.

I Built a Free URL Slug Generator with Next.js 16 — Open Source

I needed a quick slug generator for my projects and couldn’t find one that was fast, private, and supported multiple languages. So I built one.

🔗 Live: sluggenerator.app
📦 GitHub: github.com/tangwei-creater/slug-generator

What it does

  • Converts any text to a clean, SEO-friendly URL slug
  • Real-time preview as you type
  • Custom separators (hyphens, underscores, dots)
  • Unicode transliteration (ñ → n, ü → u)
  • Max length control with word-boundary awareness
  • 100% client-side — no data sent to any server

Tech stack

  • Next.js 16 (App Router + Turbopack)
  • next-intl v4 (6 languages: EN, JA, DE, ES, PT, FR)
  • Tailwind CSS v4
  • TypeScript
  • Deployed on Linux VPS + Cloudflare

SEO features built in

  • JSON-LD structured data (WebApplication, FAQPage, BlogPosting)
  • Dynamic OG images via next/og
  • Sitemap with hreflang alternates for all 6 locales
  • 5 SEO blog posts with internal linking

It’s MIT licensed. Feedback welcome!

1.153 beygirlik elektrikli Mercedes-AMG GT 4-Door Coupé, sahte V8 sesiyle geliyor [Video]

1.153 beygirlik elektrikli Mercedes-AMG GT 4-Door Coupé, sahte V8 sesiyle geliyor [Video]

1.153 beygirlik elektrikli Mercedes-AMG GT 4-Door Coupé, sahte V8 sesiyle geliyor [Video]Resmi olarak dün tanıtılan 1.153 beygirlik tamamen elektrikli otomobil modeli Mercedes-AMG GT 4-Door Coupé, sahte/dijital “V8” sesiyle geliyor. “AMGFORCE S+” adı verilen bir sistemle donatılan iddialı araç, AMG GT R’ın V8 kükremesini çok güçlü hoparlör sistemiyle dijital olarak simüle ediyor. Paylaşılan videoda duyabileceğiniz ses, elbette gerçek bir V8 kadar etkileyici değil ancak daha önce hazırlanan sahte motor seslerine kıyasla biraz daha iyi duruyor. Sahte vites geçişinin de sunulduğu bu altyapı için çok ciddi çalışmalar yapıldığı aktarılıyor. Mercedes, ses sisteminin 1.600’den fazla bağımsız ses örneği kullandığını ve seslerin gaz pedalı girdileri, hız, vites geçişleri ve sürüş davranışına göre gerçek zamanlı olarak bir araya getirildiğini belirtiyor. Yani sabit ses yerine sürüşe göre değişen bir sahte ses sistemi oluşturan Alman devi, V8 hissiyatının titreşimler ve güçlü subwoofer aracılığıyla hissedilebildiğini de söylüyor.

1.153 beygirlik elektrikli Mercedes-AMG GT 4-Door Coupé, sahte V8 sesiyle geliyor [Video] yazısı ilk olarak Teknoloji haberleri – LOG üzerinde yayınlandı.

I’m Building Apps for 14 Days Straight

Most hobby projects die in a folder.

Mine almost did too.

But 11 days ago, I decided to publicly build and ship small mobile apps every single day — no investors, no team, no “startup grind” posts. Just shipping.

Today’s status:

  • 1 app currently in Google Play Store review
  • 1 white-label app fully ready
  • Currently building: days-passed

And somehow… this tiny experiment is starting to feel real.

Day 11 Progress

Current app status

✅ 1 app submitted to the Play Store
✅ 1 reusable white-label app completed
⚒️ Working on: days-passed

Review countdown

8 days remaining for review

4/14 █████████░░░░░░░░░░░░░░░░░░░░░ 29%

Why I Started Building “Reusable” Apps

I noticed something weird:

Most indie developers build apps once.

I want to build apps that can be reused, rebranded, and shipped multiple times.

Instead of making:

  • one product → one audience

I’m experimenting with:

  • one system → many versions

Think:

  • white-label utilities
  • customizable templates
  • reusable app foundations
  • fast launch cycles

Basically: building software like LEGO blocks.

The Hardest Part Isn’t Coding

It’s consistency.

Not motivation.
Not ideas.
Not tech stacks.

Just showing up every day and continuing even when:

  • downloads are zero
  • nobody comments
  • Play Store review takes forever
  • your app feels “too simple”

Most people underestimate how powerful daily shipping becomes after a few weeks.

Current Focus: “days-passed”

Right now I’m building an app called days-passed.

Simple concept.
Tiny scope.
Fast execution.

The goal isn’t to build the next unicorn app.

The goal is to build momentum.

Because momentum compounds faster than motivation.

What I’m Learning So Far

1. Small apps ship faster than perfect apps

Perfection delays feedback.

Shipping creates feedback.

2. White-label systems are underrated

Reusable architecture saves insane amounts of time later.

3. Public progress creates accountability

Posting daily updates makes quitting harder.

And honestly?
That helps more than productivity hacks.

The Real Goal

I’m not trying to build:

  • a billion-dollar startup
  • a huge SaaS team
  • another “AI wrapper”

I just want to build software people can:

  • reuse
  • rebrand
  • launch quickly
  • make their own

And maybe document the entire process while doing it.

Day 11 done.
Still shipping.

DevSecOps for Git: Security Starts at Commit Time


Most security incidents don’t start in production.
They start with a small mistake like:

git commit -m “temporary fix”

This article explains how to implement real DevSecOps practices for Git, step by step — in a way that developers, DevOps, and security teams all understand.

1. .gitignore — First Line of Defense

Purpose

Prevent sensitive files from ever being tracked by Git.

Common files that must be ignored

  • .env, .env.*
  • *.pem, *.key, id_rsa
  • terraform.tfstate, .terraform/
  • node_modules/, dist/

Why this matters

If a file is never tracked, it can never leak.

Important limitation

.gitignore does NOT protect secrets already committed.

If a secret entered Git history once, it is already exposed.

2. Native Git Pre-Commit Hooks

What this is

A pre-commit hook is a script that Git executes automatically before every commit.

Location:
.git/hooks/pre-commit

Why it matters

  • Runs locally on the developer machine
  • Instant feedback
  • Zero CI/CD cost
  • Stops mistakes before push

How Git decides

  • Exit code 0 → Commit allowed
  • Exit code ≠ 0 → Commit blocked

This is true shift-left security.

3. Native Pre-Commit Hook (Basic Example)

A simple pre-commit hook can block obvious secrets:

  • It inspects staged changes
  • Searches for risky patterns
  • Blocks the commit if found

This approach is useful for learning, but it is not enough for real security.

4. Blocking Secret Commits with Gitleaks (Pre-Commit)

Why Gitleaks

Simple regex checks are weak.
Gitleaks adds:

  • Entropy detection
  • Cloud provider key patterns
  • Token intelligence
  • Custom rules

What happens in practice

  • Hardcoded secrets → ❌ Commit blocked
  • Placeholders or env references → ✅ Commit allowed

Result:

Secrets never leave the developer laptop.

This is prevention, not detection.

5. Repository & History Scanning with Gitleaks

Why this is required

Pre-commit hooks protect future commits.
They do nothing for past mistakes.

Repository scanning finds:

  • Secrets already committed
  • Old credentials in history
  • Legacy leaks

This step is critical for:

  • Existing repositories
  • Compliance
  • Security cleanup

6. Gitleaks in CI/CD Pipelines

Role of CI/CD

CI/CD is enforcement, not prevention.

What CI does

  • Scans code on push / pull request
  • Fails the pipeline if secrets are detected
  • Blocks merges automatically

This applies to:

  • GitHub Actions
  • GitLab CI
  • Jenkins

If CI fails, the code does not move forward.

7. Branch Protection Rules

Without branch protection, CI security checks are useless.

Mandatory rules

  • No direct push to main
  • Pull requests required
  • Required status checks
  • No force push

Security without enforcement is just documentation.

8. RBAC — Least Privilege Access

Security is also who can do what.

Recommended model

  • Developer → Create PR only
  • Maintainer → Merge PRs
  • Admin → Repository settings
  • Auditor → Read-only access

Reducing access reduces blast radius.

9. Mandatory Reviews and CODEOWNERS

Why reviews matter

Secrets often leak during:

  • Debugging
  • Infrastructure changes
  • CI/CD edits

CODEOWNERS

Automatically assigns reviewers for sensitive areas like:

  • CI pipelines
  • Infrastructure
  • Security configs

This makes security reviews default, not optional.

10. Dependabot — Supply Chain Security

Dependencies become vulnerable over time.

Dependabot:

  • Scans dependencies
  • Creates update pull requests
  • Reduces CVE exposure automatically

Supply chain security is part of DevSecOps.

Final Takeaway

DevSecOps for Git is not a single tool.

It is a layered system:

  • Prevent → Pre-commit hooks
  • Detect → Gitleaks scanning
  • Enforce → CI/CD + branch protection
  • Control → RBAC + mandatory reviews

If security starts after CI/CD, it’s already too late.

Security must start at git commit time.