DEV Community

Alex Spinov
Alex Spinov

Posted on

Convex Has a Free Backend API: Real-Time Database + Serverless Functions Without Managing Infrastructure

Your side project needs a backend. You reach for Firebase — then hit Firestore's query limitations. You try Supabase — then wrestle with row-level security policies. You set up Prisma + PlanetScale — then realize you now manage migrations, caching, and deployment.

What if your database updated your UI automatically? In real-time? Without writing a single WebSocket handler?

That's Convex.

What Convex Actually Gives You (Free Tier)

Convex combines a real-time reactive database, serverless functions, file storage, and authentication — all in one platform with a generous free tier:

  • Real-time queries — your UI updates automatically when data changes
  • ACID transactions — no more race conditions or stale reads
  • TypeScript-first — end-to-end type safety from database to frontend
  • Serverless functions — mutations, queries, actions, and scheduled jobs
  • File storage — upload and serve files without S3 configuration
  • Built-in auth — integrate with Clerk, Auth0, or custom providers

Quick Start: A Real-Time Chat in 15 Lines

npm create convex@latest
Enter fullscreen mode Exit fullscreen mode

Define your data model and functions:

// convex/messages.ts
import { mutation, query } from "./_generated/server";
import { v } from "convex/values";

export const send = mutation({
  args: { body: v.string(), author: v.string() },
  handler: async (ctx, args) => {
    await ctx.db.insert("messages", {
      body: args.body,
      author: args.author,
    });
  },
});

export const list = query({
  handler: async (ctx) => {
    return await ctx.db.query("messages").order("desc").take(50);
  },
});
Enter fullscreen mode Exit fullscreen mode

Use in React:

import { useQuery, useMutation } from "convex/react";
import { api } from "../convex/_generated/api";

function Chat() {
  const messages = useQuery(api.messages.list);
  const sendMessage = useMutation(api.messages.send);

  return (
    <div>
      {messages?.map((msg) => (
        <p key={msg._id}><b>{msg.author}:</b> {msg.body}</p>
      ))}
      <button onClick={() => sendMessage({ body: "Hello!", author: "Dev" })}>
        Send
      </button>
    </div>
  );
}
Enter fullscreen mode Exit fullscreen mode

No WebSocket setup. No polling. No cache invalidation. When you call sendMessage, every connected client sees the new message instantly.

Why Developers Are Switching to Convex

1. Reactive Queries Replace Polling

Traditional approach:

// ❌ Polling every 5 seconds
setInterval(() => fetch('/api/data').then(r => r.json()), 5000);
Enter fullscreen mode Exit fullscreen mode

Convex approach:

// ✅ Automatic real-time updates
const data = useQuery(api.myData.get);
// UI updates instantly when data changes — no polling, no stale data
Enter fullscreen mode Exit fullscreen mode

2. Transactions That Actually Work

export const transferCredits = mutation({
  args: { from: v.id("users"), to: v.id("users"), amount: v.number() },
  handler: async (ctx, { from, to, amount }) => {
    const sender = await ctx.db.get(from);
    if (sender.credits < amount) throw new Error("Insufficient credits");

    await ctx.db.patch(from, { credits: sender.credits - amount });
    await ctx.db.patch(to, { credits: (await ctx.db.get(to)).credits + amount });
    // Both operations succeed or both fail — guaranteed
  },
});
Enter fullscreen mode Exit fullscreen mode

3. Scheduled Jobs Without Cron Services

export const sendReminder = mutation({
  handler: async (ctx) => {
    // Schedule a function to run in 24 hours
    await ctx.scheduler.runAfter(24 * 60 * 60 * 1000, api.emails.sendReminder, {
      userId: "user123",
    });
  },
});
Enter fullscreen mode Exit fullscreen mode

Free Tier Limits

Resource Free Limit
Database storage 512 MB
File storage 1 GB
Function calls 1M/month
Bandwidth 1 GB
Scheduled functions Included

This is enough for MVPs, side projects, and small production apps.

When NOT to Use Convex

  • SQL joins across 10+ tables — Convex uses document-based queries (but supports relations)
  • Self-hosted requirements — it's a managed service only
  • Raw SQL queries — you write TypeScript functions, not SQL

The Bottom Line

Convex eliminates the backend setup tax. Instead of wiring up database → ORM → API routes → WebSockets → caching → deployment, you write TypeScript functions and get all of it for free.

Start here: docs.convex.dev


Need custom data extraction, scraping, or automation? I build tools that collect and process data at scale — 78 actors on Apify Store and 265+ open-source repos. Email me: Spinov001@gmail.com | My Apify Actors

Top comments (0)