Running Supabase Edge Functions Locally with tinbase
Supabase Edge Functions are useful when you need server-side logic without building a separate backend service. But during local development, setting up the complete environment around a project can add friction.
What if you could keep your local backend, database, authentication, and Edge Functions in one lightweight development environment?
This is where tinbase can be useful. It is a Supabase-compatible backend that can run locally and provides support for Edge Functions alongside database, Auth, Storage, Realtime, and Row Level Security.
In this tutorial, we will create a simple Edge Function and invoke it from a JavaScript application.
What We Are Building
The example will have this flow:
Client
↓
supabase.functions.invoke()
↓
tinbase
↓
Edge Function
↓
JSON Response
The important part is that the client can continue using the familiar Supabase SDK.
1. Create a Function
A typical Supabase project keeps Edge Functions inside:
supabase/
└── functions/
└── hello/
└── index.ts
Create index.ts:
Deno.serve(async () => {
return new Response(
JSON.stringify({
message: "Hello from the Edge Function!",
}),
{
headers: {
"Content-Type": "application/json",
},
},
);
});
The function simply returns a JSON response.
2. Start tinbase
With tinbase running locally, the backend can load functions from the project's supabase/functions directory.
The goal is to keep the local development environment simple:
npx tinbase start
You now have a local Supabase-compatible backend that can handle the function alongside your other backend services.
3. Invoke the Function
Because tinbase is compatible with the Supabase client API, you can invoke the function using supabase-js.
const { data, error } = await supabase.functions.invoke("hello");
if (error) {
console.error(error);
} else {
console.log(data);
}
The application does not need a custom HTTP wrapper just to communicate with the function.
4. Passing Data to a Function
Edge Functions become more useful when they accept input.
For example:
Deno.serve(async (req) => {
const { name } = await req.json();
return new Response(
JSON.stringify({
message: `Hello, ${name}!`,
}),
{
headers: {
"Content-Type": "application/json",
},
},
);
});
The client can send data:
const { data, er
Top comments (0)